rox-rollout 4.1.0 → 5.0.0

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.
Files changed (121) hide show
  1. checksums.yaml +5 -5
  2. data/.circleci/config.yml +51 -23
  3. data/.editorconfig +12 -0
  4. data/.github/workflows/ruby.yml +20 -0
  5. data/.gitignore +2 -0
  6. data/.rubocop.yml +17 -0
  7. data/Gemfile +2 -2
  8. data/README.md +32 -0
  9. data/Rakefile +12 -9
  10. data/bin/console +3 -4
  11. data/e2e-server/run_server.sh +12 -0
  12. data/e2e-server/server.rb +158 -0
  13. data/e2e/container.rb +11 -14
  14. data/e2e/custom_props.rb +9 -9
  15. data/e2e/rox_e2e_test.rb +18 -20
  16. data/e2e/test_vars.rb +3 -6
  17. data/example/local.rb +40 -0
  18. data/lib/rox/core/analytics.rb +18 -0
  19. data/lib/rox/core/client/buid.rb +9 -44
  20. data/lib/rox/core/client/device_properties.rb +8 -2
  21. data/lib/rox/core/client/dynamic_api.rb +53 -15
  22. data/lib/rox/core/client/internal_flags.rb +14 -2
  23. data/lib/rox/core/client/sdk_settings.rb +1 -1
  24. data/lib/rox/core/configuration/configuration.rb +1 -1
  25. data/lib/rox/core/configuration/configuration_fetched_args.rb +2 -2
  26. data/lib/rox/core/configuration/configuration_fetched_invoker.rb +8 -3
  27. data/lib/rox/core/configuration/configuration_parser.rb +39 -38
  28. data/lib/rox/core/configuration/fetcher_error.rb +1 -1
  29. data/lib/rox/core/configuration/fetcher_status.rb +1 -1
  30. data/lib/rox/core/configuration/models/experiment_model.rb +1 -1
  31. data/lib/rox/core/configuration/models/target_group_model.rb +1 -1
  32. data/lib/rox/core/consts/build.rb +3 -3
  33. data/lib/rox/core/consts/environment.rb +34 -10
  34. data/lib/rox/core/consts/property_type.rb +18 -17
  35. data/lib/rox/core/context/merged_context.rb +2 -1
  36. data/lib/rox/core/core.rb +101 -33
  37. data/lib/rox/core/entities/default_flag_values.rb +10 -0
  38. data/lib/rox/core/entities/flag.rb +22 -7
  39. data/lib/rox/core/entities/flag_setter.rb +6 -6
  40. data/lib/rox/core/entities/rox_double.rb +11 -0
  41. data/lib/rox/core/entities/rox_int.rb +11 -0
  42. data/lib/rox/core/entities/{variant.rb → rox_string.rb} +20 -13
  43. data/lib/rox/core/error_handling/exception_trigger.rb +10 -0
  44. data/lib/rox/core/error_handling/userspace_handler_exception.rb +12 -0
  45. data/lib/rox/core/error_handling/userspace_unhandled_error_invoker.rb +41 -0
  46. data/lib/rox/core/impression/impression_args.rb +2 -2
  47. data/lib/rox/core/impression/impression_invoker.rb +41 -7
  48. data/lib/rox/core/impression/models/experiment.rb +1 -1
  49. data/lib/rox/core/impression/models/reporting_value.rb +10 -2
  50. data/lib/rox/core/logging/logging.rb +3 -3
  51. data/lib/rox/core/logging/no_op_logger.rb +1 -1
  52. data/lib/rox/core/network/configuration_fetch_result.rb +1 -1
  53. data/lib/rox/core/network/configuration_fetcher.rb +9 -8
  54. data/lib/rox/core/network/configuration_fetcher_base.rb +1 -1
  55. data/lib/rox/core/network/configuration_fetcher_roxy.rb +4 -4
  56. data/lib/rox/core/network/configuration_fetcher_self_managed.rb +30 -0
  57. data/lib/rox/core/network/configuration_source.rb +1 -1
  58. data/lib/rox/core/network/request.rb +3 -3
  59. data/lib/rox/core/network/request_configuration_builder.rb +12 -9
  60. data/lib/rox/core/network/request_data.rb +1 -1
  61. data/lib/rox/core/network/response.rb +20 -4
  62. data/lib/rox/core/network/state_sender.rb +146 -0
  63. data/lib/rox/core/notifications/notification_listener.rb +4 -4
  64. data/lib/rox/core/properties/custom_property.rb +1 -1
  65. data/lib/rox/core/properties/custom_property_type.rb +1 -1
  66. data/lib/rox/core/properties/device_property.rb +2 -2
  67. data/lib/rox/core/properties/property_factory.rb +132 -0
  68. data/lib/rox/core/register/registerer.rb +13 -12
  69. data/lib/rox/core/reporting/error_reporter.rb +14 -13
  70. data/lib/rox/core/repositories/custom_property_repository.rb +1 -1
  71. data/lib/rox/core/repositories/experiment_repository.rb +2 -4
  72. data/lib/rox/core/repositories/flag_repository.rb +8 -8
  73. data/lib/rox/core/repositories/roxx/experiments_extensions.rb +8 -8
  74. data/lib/rox/core/repositories/roxx/properties_extensions.rb +32 -7
  75. data/lib/rox/core/repositories/target_group_repository.rb +2 -4
  76. data/lib/rox/core/roxx/evaluation_result.rb +2 -0
  77. data/lib/rox/core/roxx/node.rb +1 -1
  78. data/lib/rox/core/roxx/parser.rb +46 -20
  79. data/lib/rox/core/roxx/regular_expression_extensions.rb +6 -3
  80. data/lib/rox/core/roxx/string_tokenizer.rb +3 -1
  81. data/lib/rox/core/roxx/symbols.rb +1 -1
  82. data/lib/rox/core/roxx/token_type.rb +1 -1
  83. data/lib/rox/core/roxx/tokenized_expression.rb +16 -12
  84. data/lib/rox/core/roxx/value_compare_extensions.rb +49 -29
  85. data/lib/rox/core/security/signature_verifier.rb +3 -3
  86. data/lib/rox/core/security/signature_verifier_mock.rb +12 -0
  87. data/lib/rox/core/utils/debouncer.rb +18 -0
  88. data/lib/rox/core/utils/type_utils.rb +1 -1
  89. data/lib/rox/server/client/sdk_settings.rb +1 -1
  90. data/lib/rox/server/client/server_properties.rb +1 -1
  91. data/lib/rox/server/flags/normalize_flag_type.rb +25 -0
  92. data/lib/rox/server/flags/rox_double.rb +8 -0
  93. data/lib/rox/server/flags/rox_flag.rb +1 -1
  94. data/lib/rox/server/flags/rox_int.rb +8 -0
  95. data/lib/rox/server/flags/rox_string.rb +8 -0
  96. data/lib/rox/server/flags/server_entities_provider.rb +14 -4
  97. data/lib/rox/server/logging/server_logger.rb +2 -2
  98. data/lib/rox/server/rox_options.rb +39 -8
  99. data/lib/rox/server/rox_server.rb +81 -60
  100. data/lib/rox/version.rb +1 -1
  101. data/rox.gemspec +13 -9
  102. metadata +95 -36
  103. data/README_DEVELOP.md +0 -19
  104. data/_archive/.document +0 -5
  105. data/_archive/.rspec +0 -1
  106. data/_archive/Gemfile +0 -15
  107. data/_archive/Gemfile.lock +0 -87
  108. data/_archive/README.md +0 -32
  109. data/_archive/README.rdoc +0 -19
  110. data/_archive/Rakefile +0 -50
  111. data/_archive/lib/expr_function_definition.rb +0 -52
  112. data/_archive/lib/function_definition.rb +0 -48
  113. data/_archive/lib/function_token.rb +0 -12
  114. data/_archive/lib/object_extends.rb +0 -12
  115. data/_archive/lib/ruby_interpreter.rb +0 -292
  116. data/_archive/lib/stack.rb +0 -48
  117. data/_archive/lib/string_extends.rb +0 -14
  118. data/_archive/spec/ruby_interpreter_spec.rb +0 -203
  119. data/_archive/spec/spec_helper.rb +0 -30
  120. data/_archive/spec/stack_spec.rb +0 -77
  121. data/lib/rox/server/flags/rox_variant.rb +0 -8
@@ -1,48 +0,0 @@
1
- class Stack
2
-
3
- class EmptyError < StandardError
4
- end
5
-
6
- def initialize
7
- @elements = []
8
- end
9
-
10
- def push(value)
11
- @elements.push value
12
- value
13
- end
14
-
15
- def pop
16
- raise EmptyError.new('Stack is empty') if empty?
17
-
18
- @elements.pop
19
- end
20
-
21
- def poke(value, index)
22
- @elements[index] = value
23
- end
24
-
25
- def insert(value, index)
26
- @elements.insert(index, value)
27
- end
28
-
29
- def clear
30
- @elements.clear
31
- end
32
-
33
- def empty?
34
- @elements.size == 0
35
- end
36
-
37
- def to_s
38
- @elements.join(',')
39
- end
40
-
41
- def size
42
- @elements.size
43
- end
44
-
45
- def invert
46
- @elements.reverse!
47
- end
48
- end
@@ -1,14 +0,0 @@
1
-
2
- class String
3
- # convert string to float
4
- #
5
- # retval:
6
- # val - float value (or nan? if not float)
7
- # is_float - bool if val is float
8
- #
9
- def to_float
10
- fval = 0.0
11
- fval = Float(self) rescue 0.0/0.0
12
- return fval, !fval.nan?
13
- end
14
- end
@@ -1,203 +0,0 @@
1
- require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
-
3
- describe 'RubyInterpreter' do
4
- let(:parser){ RubyInterpreter.new }
5
-
6
- def check_parser_clean
7
- expect(parser.operands_stack.empty?).to eq(true)
8
- expect(parser.func_stack.empty?).to eq(true)
9
- end
10
-
11
- def check_parsing(expr, result)
12
- expect(parser.evaluateExpression(expr)).to eq(result)
13
- check_parser_clean
14
- end
15
-
16
- def check_parser_clean2
17
- expect(parser.expr_stack.empty?).to eq(true)
18
- end
19
-
20
- def check_parsing2(expr, result)
21
- expect(parser.evaluateExpression2(expr)).to eq(result)
22
- check_parser_clean2
23
- end
24
-
25
- context 'and function' do
26
- it 'checks and(true,true) == true' do
27
- check_parsing2('and(true, true)', true)
28
- end
29
-
30
- it 'checks and(true,false) == false' do
31
- check_parsing2('and(true, false)', false)
32
- end
33
-
34
- it 'checks and(false,true) == false' do
35
- check_parsing2('and(false, true)', false)
36
- end
37
-
38
- it 'checks and(false,false) == false' do
39
- check_parsing2('and(false, false)', false)
40
- end
41
- end
42
-
43
- context 'or function' do
44
- it 'checks or(true, true) == true' do
45
- check_parsing2('or(true, true)', true)
46
- end
47
-
48
- it 'checks or(true, false) == true' do
49
- check_parsing2('or(true, false)', true)
50
- end
51
-
52
- it 'checks or(false, true) == true' do
53
- check_parsing2('or(false, true)', true)
54
- end
55
-
56
- it 'checks or(false, false) == false' do
57
- check_parsing2('or(false, false)', false)
58
- end
59
- end
60
-
61
- context 'not function' do
62
- it 'checks not(false) == true' do
63
- check_parsing2('not(false)', true)
64
- end
65
-
66
- it 'checks not(true) == false' do
67
- check_parsing2('not(true)', false)
68
- end
69
-
70
- it 'checks not(undefined) == false' do
71
- check_parsing2('not(undefined)', true)
72
- end
73
- end
74
-
75
- context 'eq function' do
76
- it 'checks eq("la la", "la la")) == true' do
77
- check_parsing2('eq("la la", "la la")', true);
78
- end
79
-
80
- it 'checks eq("la la", "la,la")) == false' do
81
- check_parsing2('eq("la la", "la,la")', false);
82
- end
83
-
84
- it 'checks eq("lala", "lala") == true' do
85
- check_parsing2('eq("lala", "lala")', true)
86
- end
87
-
88
- it 'checks eq(undefined, undefined) == true' do
89
- check_parsing2('eq(undefined, undefined)', true)
90
- end
91
- end
92
-
93
- context 'lt function' do
94
- it 'checks lt(500,100) == false' do
95
- check_parsing2('lt(500, 100)', false)
96
- end
97
-
98
- it 'checks lt(500,500) == false' do
99
- check_parsing2('lt(500, 500)', false)
100
- end
101
-
102
- it 'checks lt(500,500.54) == true' do
103
- check_parsing2('lt(500, 500.54)', true)
104
- end
105
- end
106
-
107
- context 'lte function' do
108
- it 'checks lte(500, 500) == true' do
109
- check_parsing2('lte(500, 500)', true)
110
- end
111
- end
112
-
113
- context 'gt function' do
114
- it 'checks gt(500, 100) == true' do
115
- check_parsing2('gt(500,100)',true)
116
- end
117
-
118
- it 'checks gt(500, 500) == false' do
119
- check_parsing2('gt(500,500)',false)
120
- end
121
-
122
- it 'checks gt(500.54, 500) == true' do
123
- check_parsing2('gt(500.54,500)',true)
124
- end
125
- end
126
-
127
- context 'gte function' do
128
- it 'checks gte(500, 500) == true' do
129
- check_parsing2('gte(500,500)',true)
130
- end
131
-
132
- it 'checks gte("500", 500) == false' do
133
- check_parsing2('gte("500",500)',false)
134
- end
135
- end
136
-
137
- context 'isUndefined function' do
138
- it 'checks isUndefined(undefined) == true' do
139
- check_parsing2('isUndefined(undefined)', true)
140
- end
141
-
142
- it 'checks isUndefined("undefined") == false' do
143
- check_parsing2('isUndefined("undefined")', false)
144
- end
145
-
146
- it 'checks isUndefined(123123) == false' do
147
- check_parsing2('isUndefined(123123)', false)
148
- end
149
- end
150
-
151
- context 'now() function' do
152
- it 'checks gte(now(), now()) == true' do
153
- check_parsing2('gte(now(), now())', true)
154
- end
155
-
156
- it 'checks gte(now(), 2458.123) == true' do
157
- check_parsing2('gte(now(), 2458.123)', true)
158
- end
159
- end
160
-
161
- context 'complex checks' do
162
- it 'checks and(true, or(true, true)) == true' do
163
- check_parsing2('and(true, or(true, true))', true);
164
- end
165
-
166
- it 'checks and(true, or(false, true)) == true' do
167
- check_parsing2('and(true, or(false, true))', true);
168
- end
169
-
170
- it 'checks and(true, or(false, false)) == false' do
171
- check_parsing2('and(true, or(false, false))', false);
172
- end
173
-
174
- it 'checks not(and(false, or(false, true))) == true' do
175
- check_parsing2('not(and(false, or(false, true)))', true);
176
- end
177
-
178
- it 'checks ne(100.123, 100.321) == true' do
179
- check_parsing2('ne(100.123, 100.321)', true)
180
- end
181
-
182
- it 'checks not(eq(undefined, undefined)) == false' do
183
- check_parsing('not(eq(undefined, undefined))', 'false')
184
- end
185
-
186
- it 'checks not(eq(not(undefined), not(undefined))) == true' do
187
- check_parsing2('not(eq(not(undefined), not(undefined)))', true )
188
- end
189
-
190
- end
191
-
192
- context 'error checking' do
193
- it 'checks NOT_AN_OPERATOR(500, 500) == false' do
194
- check_parsing('NOT_AN_OPERATOR(500,500)', 'false')
195
- end
196
-
197
- it 'checks JUSTAWORD(500, 500) == false' do
198
- check_parsing('JUSTAWORD(500,500)', 'false')
199
- end
200
- end
201
-
202
- #todo check non-matched pairs
203
- end
@@ -1,30 +0,0 @@
1
- require 'simplecov'
2
-
3
- module SimpleCov::Configuration
4
- def clean_filters
5
- @filters = []
6
- end
7
- end
8
-
9
- SimpleCov.configure do
10
- clean_filters
11
- load_adapter 'test_frameworks'
12
- end
13
-
14
- ENV["COVERAGE"] && SimpleCov.start do
15
- add_filter "/.rvm/"
16
- end
17
- $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
18
- $LOAD_PATH.unshift(File.dirname(__FILE__))
19
-
20
- require 'rspec'
21
- require 'ruby_interpreter'
22
- require 'stack'
23
-
24
- # Requires supporting files with custom matchers and macros, etc,
25
- # in ./support/ and its subdirectories.
26
- Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f}
27
-
28
- RSpec.configure do |config|
29
-
30
- end
@@ -1,77 +0,0 @@
1
- require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
-
3
- describe 'Stack' do
4
- let(:stack) { Stack.new }
5
-
6
- it 'should push item' do
7
- stack.push 'a'
8
- stack.push 'b'
9
- expect(stack.to_s).to eq('a,b')
10
- end
11
-
12
- it 'should pop item' do
13
- stack.push 'a'
14
- stack.push 'b'
15
- item = stack.pop
16
-
17
- expect(stack.to_s).to eq('a')
18
- expect(item).to eq('b')
19
- end
20
-
21
- it 'should raise exception on poping from emtpy stack' do
22
- stack.clear
23
- expect{ stack.pop }.to raise_error(Stack::EmptyError)
24
- end
25
-
26
- it 'can be cleared' do
27
- stack.push 'a'
28
- stack.clear
29
- expect(stack.empty?).to eq(true)
30
- end
31
-
32
- it 'to_s display valid' do
33
- stack.push 'a'
34
- stack.push 'b'
35
- stack.push 'c'
36
- expect(stack.to_s).to eq('a,b,c')
37
- end
38
-
39
- it 'empty? handles' do
40
- stack.clear
41
- expect(stack.empty?).to eq(true)
42
-
43
- stack.push 'a'
44
- expect(stack.empty?).to eq(false)
45
- end
46
-
47
- it 'can return size' do
48
- stack.clear
49
- expect(stack.size).to eq(0)
50
-
51
- stack.push 'a'
52
- expect(stack.size).to eq(1)
53
- end
54
-
55
- it 'can poke at specific index' do
56
- stack.push 'a'
57
- stack.push 'b'
58
- stack.poke 'c', 0
59
- expect(stack.to_s).to eq('c,b')
60
- end
61
-
62
- it 'can insert value at index' do
63
- stack.push 'a'
64
- stack.push 'b'
65
- stack.insert 'c', 1
66
-
67
- expect(stack.to_s).to eq('a,c,b')
68
- end
69
-
70
- it 'can invert order of stack' do
71
- stack.push 'a'
72
- stack.push 'b'
73
- stack.invert
74
-
75
- expect(stack.to_s).to eq('b,a')
76
- end
77
- end
@@ -1,8 +0,0 @@
1
- require 'rox/core/entities/variant'
2
-
3
- module Rox
4
- module Server
5
- class RoxVariant < Rox::Core::Variant
6
- end
7
- end
8
- end