rule_engine_client 0.1.14 → 0.1.15

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 (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/rule_engine_client.rb +161 -163
  3. metadata +5 -5
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 9b1a8c9b6eb9a607d635b566a2af02cc2d030a6167fd62b4bb6f85c2ace1bbef
4
- data.tar.gz: dc62fc28e9c85659cbb069484f129fdc2577bd285e06b99c6ee23378215e5429
3
+ metadata.gz: 43f25de086c6b5cc8a77bb6c456e8f6d9a00a2648608ba8480289af653522590
4
+ data.tar.gz: a8bd4f5f717195d9f89a06c5ba4c9e4d4f854160af4ac13e8ac56e175fa20b92
5
5
  SHA512:
6
- metadata.gz: 5630592647ac4066156880b42a6ebe8b75f938a1fdbd02a6fed0f1f84db21363148600e4816ee7736b8ccf8ec1bca561fb268b4a2511b1706ef5f93ad492fa3d
7
- data.tar.gz: 63aabb4250fb31f68419211894eaab84f0fc0c28941f66839131c69b4cd95abc4d0fd8550074f3b47b6c0c0d22cd4e1bc10066eced3bca081699fd4c140d5bdc
6
+ metadata.gz: 886543fd56e1aeb6d4d4f40c2e94c2f6635a45d755b32e7c4bed3e77c28cccd7a2e190417c79211a041a7fa00dfa66d4f24b7a57479410575908f04e01b8ee69
7
+ data.tar.gz: fd0a3f8011a6952bea2593d28b7c4d73d5e16408acd8ddcffc68456405b058d66d9970b8bdf4fddee0862416cf651ef0792539f60064d8d72cb5d71eea2a8f8d
@@ -1,163 +1,161 @@
1
- require 'net/http'
2
- require 'json'
3
- require 'logger'
4
- require 'timeout'
5
- require 'digest/md5'
6
-
7
- # rule engine client class
8
- class RuleEngineClient
9
- def initialize(server = 'http://localhost:8088', request_timeout_in_s = 5, verbose = false)
10
- @server = server
11
- @verbose = verbose
12
- @logger = Logger.new($stdout)
13
- @request_timeout_in_s = request_timeout_in_s
14
- @user_name = 'areej'
15
- @password = '123456'
16
- log("'#{server}' client is initialized")
17
- end
18
-
19
- def evaluate(engine, params, mode = 'production')
20
- url = URI.parse("#{@server}/run?e=#{engine}&m=#{mode}")
21
- log("params #{params}")
22
- params = params_mapper(params, engine)
23
- @result = create_request(url, 'POST', params)
24
- response = response_builder
25
- log("response #{response}")
26
- response
27
- end
28
-
29
- def engine_exists(engine)
30
- log("checking if engine (#{engine}) exists")
31
- response = export_engine(engine)
32
- response['body'] = {
33
- 'exists' => !response['body'].empty?
34
- }
35
- response
36
- end
37
-
38
- def get_engine_models(engine)
39
- response = export_engine(engine)
40
- models = !response['body'].empty? ? response['body']['model'] : {}
41
- models_keys = models.keys
42
- models_keys.each do |key|
43
- get_nested_object(models, models[key]['properties'])
44
- end
45
- models
46
- end
47
-
48
- def get_nested_object(models, props)
49
- props.each do |prop|
50
- if prop['typeconcept'] && (prop['typeconcept'].is_a? String)
51
- prop['typeconcept'] = models[prop['typeconcept']]
52
- prop['typeconcept']['properties'] = get_nested_object(models, prop['typeconcept']['properties'])
53
- end
54
- end
55
- end
56
-
57
- private
58
-
59
- def log(message)
60
- @logger.debug("rule engine: #{message}") if @verbose
61
- end
62
-
63
- def valid_json?(obj)
64
- !!JSON.parse(obj)
65
- rescue StandardError
66
- false
67
- end
68
-
69
- def response_hash(code, body, errors)
70
- {
71
- 'code' => code,
72
- 'body' => body,
73
- 'errors' => errors
74
- }
75
- end
76
-
77
- def response_builder
78
- if @time_out
79
- errors = ['HTTP Gateway timeout!']
80
- body = {}
81
- code = 504
82
- elsif @result.code == '502'
83
- errors = ['rule engine server down']
84
- body = {}
85
- code = @result.code
86
- elsif !valid_json?(@result.body)
87
- errors = ['could not parse response body to JSON']
88
- body = {}
89
- code = 500
90
- else
91
- body = JSON.parse(@result.body)
92
- errors = body['errors'] || []
93
- body = body.except('errors', 'status')
94
- code = @result.code
95
- end
96
- response_hash(code, body, errors)
97
- end
98
-
99
- def create_request(url, request_type, params = {})
100
- Timeout.timeout(@request_timeout_in_s) do
101
- http = Net::HTTP.new(url.host, url.port)
102
- http.use_ssl = true if url.instance_of? URI::HTTPS
103
- if request_type == 'GET'
104
- log("Will send get request: #{url}")
105
- request = Net::HTTP::Get.new(url.request_uri)
106
- else
107
- log("Will send post request: #{url}")
108
- request = Net::HTTP::Post.new(url.request_uri)
109
- request.body = params.to_json
110
- log("request body created #{request.body} ")
111
- end
112
- request.basic_auth(@user_name, @password)
113
- request['Content-Type'] = 'application/json'
114
- request['Accept'] = 'application/json'
115
- http.request(request)
116
- end
117
- rescue Timeout::Error
118
- log('HTTP Gateway timeout!')
119
- @time_out = true
120
- end
121
-
122
- def export_engine(engine)
123
- url = URI.parse("#{@server}/engine/export?e=#{engine}")
124
- @result = create_request(url, 'GET')
125
- response_builder
126
- end
127
-
128
- def params_mapper(params, engine)
129
- @models = get_engine_models(engine)
130
- @models_keys = @models.keys
131
- params_keys = params.keys
132
- params_keys.each do |key|
133
- if !@models_keys.include? key
134
- params.delete(key)
135
- else
136
- props = @models[key]['properties'].map do |prop|
137
- prop['name']
138
- end
139
- filter_nested_params(params, key, props)
140
- end
141
- end
142
- log("filtered params #{params}")
143
- params
144
- end
145
-
146
- def filter_nested_params(params, key, props)
147
- keys = params[key].keys
148
- keys.each do |el|
149
- if !props.include? el
150
- params[key].delete(el)
151
- elsif params[key][el].is_a? Hash
152
- nested_el = @models[key]['properties'].find { |obj| obj['name'] == el }
153
- if nested_el['datatype'] != 'object'
154
- params[key].delete(el)
155
- elsif nested_el && !nested_el['typeconcept']['any']
156
- el_props = nested_el['typeconcept']['properties']
157
- filter_nested_params(params[key], el, el_props) if el_props.length
158
- end
159
- end
160
- end
161
- params
162
- end
163
- end
1
+ require 'net/http'
2
+ require 'json'
3
+ require 'logger'
4
+ require 'timeout'
5
+ require 'digest/md5'
6
+
7
+ # rule engine client class
8
+ class RuleEngineClient
9
+ def initialize(server = 'http://localhost:8088', request_timeout_in_s = 5, verbose = false)
10
+ @server = server
11
+ @verbose = verbose
12
+ @logger = Logger.new($stdout)
13
+ @request_timeout_in_s = request_timeout_in_s
14
+ log("'#{server}' client is initialized")
15
+ end
16
+
17
+ def evaluate(engine, params, mode = 'production')
18
+ url = URI.parse("#{@server}/run?e=#{engine}&m=#{mode}")
19
+ log("params #{params}")
20
+ params = params_mapper(params, engine)
21
+ @result = create_request(url, 'POST', params)
22
+ response = response_builder
23
+ log("response #{response}")
24
+ response
25
+ end
26
+
27
+ def engine_exists(engine)
28
+ log("checking if engine (#{engine}) exists")
29
+ response = export_engine(engine)
30
+ response['body'] = {
31
+ 'exists' => !response['body'].empty?
32
+ }
33
+ response
34
+ end
35
+
36
+ def get_engine_models(engine)
37
+ response = export_engine(engine)
38
+ models = !response['body'].empty? ? response['body']['model'] : {}
39
+ models_keys = models.keys
40
+ models_keys.each do |key|
41
+ get_nested_object(models, models[key]['properties'])
42
+ end
43
+ models
44
+ end
45
+
46
+ def get_nested_object(models, props)
47
+ props.each do |prop|
48
+ if prop['typeconcept'] && (prop['typeconcept'].is_a? String)
49
+ prop['typeconcept'] = models[prop['typeconcept']]
50
+ prop['typeconcept']['properties'] = get_nested_object(models, prop['typeconcept']['properties'])
51
+ end
52
+ end
53
+ end
54
+
55
+ private
56
+
57
+ def log(message)
58
+ @logger.debug("rule engine: #{message}") if @verbose
59
+ end
60
+
61
+ def valid_json?(obj)
62
+ !!JSON.parse(obj)
63
+ rescue StandardError
64
+ false
65
+ end
66
+
67
+ def response_hash(code, body, errors)
68
+ {
69
+ 'code' => code,
70
+ 'body' => body,
71
+ 'errors' => errors
72
+ }
73
+ end
74
+
75
+ def response_builder
76
+ if @time_out
77
+ errors = ['HTTP Gateway timeout!']
78
+ body = {}
79
+ code = 504
80
+ elsif @result.code == '502'
81
+ errors = ['rule engine server down']
82
+ body = {}
83
+ code = @result.code
84
+ elsif !valid_json?(@result.body)
85
+ errors = ['could not parse response body to JSON']
86
+ body = {}
87
+ code = 500
88
+ else
89
+ body = JSON.parse(@result.body)
90
+ errors = body['errors'] || []
91
+ body = body.except('errors', 'status')
92
+ code = @result.code
93
+ end
94
+ response_hash(code, body, errors)
95
+ end
96
+
97
+ def create_request(url, request_type, params = {})
98
+ Timeout.timeout(@request_timeout_in_s) do
99
+ http = Net::HTTP.new(url.host, url.port)
100
+ http.use_ssl = true if url.instance_of? URI::HTTPS
101
+ if request_type == 'GET'
102
+ log("Will send get request: #{url}")
103
+ request = Net::HTTP::Get.new(url.request_uri)
104
+ else
105
+ log("Will send post request: #{url}")
106
+ request = Net::HTTP::Post.new(url.request_uri)
107
+ request.body = params.to_json
108
+ log("request body created #{request.body} ")
109
+ end
110
+ # request.basic_auth(@user_name, @password)
111
+ request['Content-Type'] = 'application/json'
112
+ request['Accept'] = 'application/json'
113
+ http.request(request)
114
+ end
115
+ rescue Timeout::Error
116
+ log('HTTP Gateway timeout!')
117
+ @time_out = true
118
+ end
119
+
120
+ def export_engine(engine)
121
+ url = URI.parse("#{@server}/engine/export?e=#{engine}")
122
+ @result = create_request(url, 'GET')
123
+ response_builder
124
+ end
125
+
126
+ def params_mapper(params, engine)
127
+ @models = get_engine_models(engine)
128
+ @models_keys = @models.keys
129
+ params_keys = params.keys
130
+ params_keys.each do |key|
131
+ if !@models_keys.include? key
132
+ params.delete(key)
133
+ else
134
+ props = @models[key]['properties'].map do |prop|
135
+ prop['name']
136
+ end
137
+ filter_nested_params(params, key, props)
138
+ end
139
+ end
140
+ log("filtered params #{params}")
141
+ params
142
+ end
143
+
144
+ def filter_nested_params(params, key, props)
145
+ keys = params[key].keys
146
+ keys.each do |el|
147
+ if !props.include? el
148
+ params[key].delete(el)
149
+ elsif params[key][el].is_a? Hash
150
+ nested_el = @models[key]['properties'].find { |obj| obj['name'] == el }
151
+ if nested_el['datatype'] != 'object'
152
+ params[key].delete(el)
153
+ elsif nested_el && !nested_el['typeconcept']['any']
154
+ el_props = nested_el['typeconcept']['properties']
155
+ filter_nested_params(params[key], el, el_props) if el_props.length
156
+ end
157
+ end
158
+ end
159
+ params
160
+ end
161
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rule_engine_client
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.14
4
+ version: 0.1.15
5
5
  platform: ruby
6
6
  authors:
7
7
  - Areej Nour
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-08-29 00:00:00.000000000 Z
11
+ date: 2023-01-03 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: integration with rule server
14
14
  email:
@@ -23,7 +23,7 @@ licenses:
23
23
  - MIT
24
24
  metadata:
25
25
  homepage_uri: https://rubygems.org/gems/rule_engine_client
26
- post_install_message:
26
+ post_install_message:
27
27
  rdoc_options: []
28
28
  require_paths:
29
29
  - lib
@@ -39,7 +39,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
39
39
  version: '0'
40
40
  requirements: []
41
41
  rubygems_version: 3.3.7
42
- signing_key:
42
+ signing_key:
43
43
  specification_version: 4
44
44
  summary: Rule Engine Client
45
45
  test_files: []