moesif_api 1.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.
@@ -0,0 +1,72 @@
1
+
2
+
3
+ require 'date'
4
+ module MoesifApi
5
+ class ResponseModel < BaseModel
6
+ # Time when response received
7
+ # @return [DateTime]
8
+ attr_accessor :time
9
+
10
+ # HTTP Status code such as 200
11
+ # @return [Integer]
12
+ attr_accessor :status
13
+
14
+ # Key/Value map of response headers
15
+ # @return [Object]
16
+ attr_accessor :headers
17
+
18
+ # Response body
19
+ # @return [Object]
20
+ attr_accessor :body
21
+
22
+ # IP Address from the response, such as the server IP Address
23
+ # @return [String]
24
+ attr_accessor :ip_address
25
+
26
+ # A mapping from model property names to API property names
27
+ def self.names
28
+ if @hash.nil?
29
+ @hash = {}
30
+ @hash["time"] = "time"
31
+ @hash["status"] = "status"
32
+ @hash["headers"] = "headers"
33
+ @hash["body"] = "body"
34
+ @hash["ip_address"] = "ip_address"
35
+ end
36
+ @hash
37
+ end
38
+
39
+ def initialize(time = nil,
40
+ status = nil,
41
+ headers = nil,
42
+ body = nil,
43
+ ip_address = nil)
44
+ @time = time
45
+ @status = status
46
+ @headers = headers
47
+ @body = body
48
+ @ip_address = ip_address
49
+ end
50
+
51
+ # Creates an instance of the object from a hash
52
+ def self.from_hash(hash)
53
+ if hash == nil
54
+ nil
55
+ else
56
+ # Extract variables from the hash
57
+ time = DateTime.iso8601(hash["time"]) if hash["time"]
58
+ status = hash["status"]
59
+ headers = hash["headers"]
60
+ body = hash["body"]
61
+ ip_address = hash["ip_address"]
62
+
63
+ # Create object from extracted values
64
+ ResponseModel.new(time,
65
+ status,
66
+ headers,
67
+ body,
68
+ ip_address)
69
+ end
70
+ end
71
+ end
72
+ end
@@ -0,0 +1,44 @@
1
+
2
+
3
+ module MoesifApi
4
+ class StatusModel < BaseModel
5
+ # Status of Call
6
+ # @return [Boolean]
7
+ attr_accessor :status
8
+
9
+ # Location
10
+ # @return [String]
11
+ attr_accessor :region
12
+
13
+ # A mapping from model property names to API property names
14
+ def self.names
15
+ if @hash.nil?
16
+ @hash = {}
17
+ @hash["status"] = "status"
18
+ @hash["region"] = "region"
19
+ end
20
+ @hash
21
+ end
22
+
23
+ def initialize(status = nil,
24
+ region = nil)
25
+ @status = status
26
+ @region = region
27
+ end
28
+
29
+ # Creates an instance of the object from a hash
30
+ def self.from_hash(hash)
31
+ if hash == nil
32
+ nil
33
+ else
34
+ # Extract variables from the hash
35
+ status = hash["status"]
36
+ region = hash["region"]
37
+
38
+ # Create object from extracted values
39
+ StatusModel.new(status,
40
+ region)
41
+ end
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,22 @@
1
+
2
+
3
+ module MoesifApi
4
+ class MoesifAPIClient
5
+ # Singleton access to api controller
6
+ # @return [ApiController] Returns the controller instance
7
+ def api
8
+ ApiController.instance
9
+ end
10
+
11
+ # Singleton access to health controller
12
+ # @return [HealthController] Returns the controller instance
13
+ def health
14
+ HealthController.instance
15
+ end
16
+
17
+ # Initializer with authentication and configuration parameters
18
+ def initialize(application_id: nil)
19
+ Configuration.application_id = application_id
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,29 @@
1
+
2
+
3
+ require 'json'
4
+ require 'test/unit'
5
+ require 'moesif_api.rb'
6
+ require_relative '../test_helper.rb'
7
+ require_relative '../http_response_catcher.rb'
8
+
9
+ class ControllerTestBase < Test::Unit::TestCase
10
+ include MoesifApi
11
+
12
+ class << self
13
+ attr_accessor :controller
14
+ end
15
+
16
+ # Called only once for a test class before any test has executed.
17
+ def self.startup
18
+ @@api_client = MoesifAPIClient.new
19
+ @@request_timeout = 30
20
+ @@assert_precision = 0.01
21
+ Configuration.application_id = "eyJhcHAiOiIzNjU6NiIsInZlciI6IjIuMCIsIm9yZyI6IjM1OTo0IiwiaWF0IjoxNDczMzc5MjAwfQ.9WOx3D357PGMxrXzFm3pV3IzJSYNsO4oRudiMI8mQ3Q"
22
+ end
23
+
24
+ # Called once before every test case.
25
+ def setup
26
+ @response_catcher = HttpResponseCatcher.new
27
+ self.class.controller.http_call_back = @response_catcher
28
+ end
29
+ end
@@ -0,0 +1,35 @@
1
+
2
+
3
+ require_relative 'controller_test_base'
4
+
5
+ class ApiControllerTests < ControllerTestBase
6
+ # Called only once for the class before any test has executed
7
+ def self.startup
8
+ self.controller = @@api_client.api
9
+ end
10
+
11
+ # Add Single Event via Injestion API
12
+ def test_add_event()
13
+ # Parameters for the API call
14
+ body = EventModel.from_hash(JSON.parse('{ "request": { "time": "2016-09-09T04:45:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:45:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "23jdf0owekfmcn4u3qypxg09w4d8ayrcdx8nu2ng]s98y18cx98q3yhwmnhcfx43f" }'))
15
+
16
+ # Perform the API call through the SDK function
17
+ self.class.controller.create_event(body)
18
+
19
+ # Test response code
20
+ assert_equal(@response_catcher.response.status_code, 201)
21
+ end
22
+
23
+ # Add Batched Events via Ingestion API
24
+ def test_add_batched_events()
25
+ # Parameters for the API call
26
+ body = JSON.parse('[{ "request": { "time": "2016-09-09T04:45:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:45:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "23jdf0owekfmcn4u3qypxg09w4d8ayrcdx8nu2ng]s98y18cx98q3yhwmnhcfx43f" }, { "request": { "time": "2016-09-09T04:46:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:46:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "23jdf0owekfmcn4u3qypxg09w4d8ayrcdx8nu2ng]s98y18cx98q3yhwmnhcfx43f" }, { "request": { "time": "2016-09-09T04:47:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:47:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "23jdf0owekfmcn4u3qypxg09w4d8ayrcdx8nu2ng]s98y18cx98q3yhwmnhcfx43f" }, { "request": { "time": "2016-09-09T04:48:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:48:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "exfzweachxjgznvKUYrxFcxv]s98y18cx98q3yhwmnhcfx43f" }, { "request": { "time": "2016-09-09T04:49:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:49:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "mndug437f43", "session_token": "23jdf0owekfmcn4u3qypxg09w4d8ayrcdx8nu2ng]s98y18cx98q3yhwmnhcfx43f" }, { "request": { "time": "2016-09-09T04:50:42.914", "uri": "https://api.acmeinc.com/items/reviews/", "verb": "PATCH", "api_version": "1.1.0", "ip_address": "61.48.220.123", "headers": { "Host": "api.acmeinc.com", "Accept": "*/*", "Connection": "Keep-Alive", "User-Agent": "Dalvik/2.1.0 (Linux; U; Android 5.0.2; C6906 Build/14.5.A.0.242)", "Content-Type": "application/json", "Content-Length": "126", "Accept-Encoding": "gzip" }, "body": { "items": [ { "direction_type": 1, "discovery_id": "fwfrf", "liked": false }, { "direction_type": 2, "discovery_id": "d43d3f", "liked": true } ] } }, "response": { "time": "2016-09-09T04:50:42.914", "status": 500, "headers": { "Date": "Tue, 23 Aug 2016 23:46:49 GMT", "Vary": "Accept-Encoding", "Pragma": "no-cache", "Expires": "-1", "Content-Type": "application/json; charset=utf-8", "X-Powered-By": "ARR/3.0", "Cache-Control": "no-cache", "Arr-Disable-Session-Affinity": "true" }, "body": { "Error": "InvalidArgumentException", "Message": "Missing field field_a" } }, "user_id": "recvreedfef", "session_token": "xcvkrjmcfghwuignrmcmhxdhaaezse4w]s98y18cx98q3yhwmnhcfx43f" } ]').map{|element| EventModel.from_hash(element)}
27
+
28
+ # Perform the API call through the SDK function
29
+ self.class.controller.create_events_batch(body)
30
+
31
+ # Test response code
32
+ assert_equal(@response_catcher.response.status_code, 201)
33
+ end
34
+
35
+ end
@@ -0,0 +1,16 @@
1
+
2
+
3
+ class HttpResponseCatcher < MoesifApi::HttpCallBack
4
+ attr_accessor :response
5
+
6
+ def on_before_request(request)
7
+ end
8
+
9
+ # Catching the response
10
+ def on_after_response(context)
11
+ @response = context.response
12
+ end
13
+ end
14
+
15
+
16
+
@@ -0,0 +1,94 @@
1
+
2
+
3
+ require 'tempfile'
4
+ require 'open-uri'
5
+
6
+ class TestHelper
7
+
8
+ @cache = Hash.new
9
+
10
+ # Class method to compare the received headers with the expected headers.
11
+ # @param [Hash] A hash of expected headers (keys in lower case).
12
+ # @param [Hash] A hash of received headers.
13
+ # @param [Boolean, optional] A flag which determines if we allow extra headers.
14
+ def self.match_headers(expected_headers,
15
+ received_headers,
16
+ allow_extra: true)
17
+ return false if ((received_headers.length < expected_headers.length) ||
18
+ ((allow_extra == false) && (received_headers.length > expected_headers.length)))
19
+
20
+ received_headers = Hash[received_headers.map{|k, v| [k.to_s.downcase, v]}]
21
+ expected_headers.each do |e_key, e_value|
22
+ return false unless received_headers.key?(e_key)
23
+ return false if ((e_value != nil) &&
24
+ (e_value != received_headers[e_key]))
25
+ end
26
+
27
+ return true
28
+ end
29
+
30
+ # Class method to compare the received body with the expected body.
31
+ # @param [Dynamic] The expected body.
32
+ # @param [Dynamic] The received body.
33
+ # @param [Boolean, optional] A flag which determines if we check values in dictionaries.
34
+ # @param [Boolean, optional] A flag which determines if we check the order of array elements.
35
+ # @param [Boolean, optional] A flag which determines if we check the count of array elements.
36
+ def self.match_body(expected_body,
37
+ received_body,
38
+ check_values: false,
39
+ check_order: false,
40
+ check_count: false)
41
+ if expected_body.instance_of? Hash
42
+ return False if not received_body.instance_of? Hash
43
+ for key in expected_body.keys
44
+ return false if not received_body.keys.include? key
45
+ if check_values or expected_body[key].instance_of? Hash
46
+ return false if not TestHelper.match_body(expected_body[key],
47
+ received_body[key],
48
+ check_values: check_values,
49
+ check_order: check_order,
50
+ check_count: check_count)
51
+ end
52
+ end
53
+ elsif expected_body.instance_of? Array
54
+ return False if not received_body.instance_of? Array
55
+ if check_count == true && (expected_body.length != received_body.length)
56
+ return false
57
+ else
58
+ previous_matches = Array.new
59
+ expected_body.each.with_index do |expected_element, i|
60
+ matches = (received_body.map.with_index do |received_element, j|
61
+ j if TestHelper.match_body(expected_element,
62
+ received_element,
63
+ check_values: check_values,
64
+ check_order: check_order,
65
+ check_count: check_count)
66
+ end).compact
67
+ return false if matches.length == 0
68
+ if check_order == true
69
+ return false if (i != 0 && matches.map{|x| previous_matches.map{|y| y > x}.all?}.all?)
70
+ previous_matches = matches
71
+ end
72
+ end
73
+ end
74
+ elsif expected_body != received_body
75
+ return false
76
+ end
77
+ return true
78
+ end
79
+
80
+ # Class method which takes a URL, downloads the file (if not already downloaded
81
+ # for this test session) and returns a file object for the file in read-binary mode.
82
+ # @param [String] The URL of the required file.
83
+ def self.get_file(url)
84
+ if not @cache.keys.include? url
85
+ @cache[url] = Tempfile.new('APIMatic')
86
+ @cache[url].binmode
87
+ @cache[url].write(open(url, {ssl_verify_mode: OpenSSL::SSL::VERIFY_NONE}).read)
88
+ else
89
+ @cache[url].open
90
+ @cache[url].binmode
91
+ end
92
+ return @cache[url]
93
+ end
94
+ end
metadata ADDED
@@ -0,0 +1,112 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: moesif_api
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Moesif, Inc
8
+ - Derric Gilling
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2016-09-09 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ~>
18
+ - !ruby/object:Gem::Version
19
+ version: 3.1.5
20
+ name: test-unit
21
+ prerelease: false
22
+ type: :runtime
23
+ version_requirements: !ruby/object:Gem::Requirement
24
+ requirements:
25
+ - - ~>
26
+ - !ruby/object:Gem::Version
27
+ version: 3.1.5
28
+ - !ruby/object:Gem::Dependency
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ~>
32
+ - !ruby/object:Gem::Version
33
+ version: 1.1.2
34
+ name: unirest
35
+ prerelease: false
36
+ type: :runtime
37
+ version_requirements: !ruby/object:Gem::Requirement
38
+ requirements:
39
+ - - ~>
40
+ - !ruby/object:Gem::Version
41
+ version: 1.1.2
42
+ - !ruby/object:Gem::Dependency
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: 0.2.1
48
+ name: json_mapper
49
+ prerelease: false
50
+ type: :runtime
51
+ version_requirements: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - ~>
54
+ - !ruby/object:Gem::Version
55
+ version: 0.2.1
56
+ description: Collection/Data Ingestion API
57
+ email: derric@moesif.com
58
+ executables: []
59
+ extensions: []
60
+ extra_rdoc_files: []
61
+ files:
62
+ - LICENSE
63
+ - README.md
64
+ - lib/moesif_api.rb
65
+ - lib/moesif_api/api_helper.rb
66
+ - lib/moesif_api/configuration.rb
67
+ - lib/moesif_api/controllers/api_controller.rb
68
+ - lib/moesif_api/controllers/base_controller.rb
69
+ - lib/moesif_api/controllers/health_controller.rb
70
+ - lib/moesif_api/exceptions/api_exception.rb
71
+ - lib/moesif_api/http/http_call_back.rb
72
+ - lib/moesif_api/http/http_client.rb
73
+ - lib/moesif_api/http/http_context.rb
74
+ - lib/moesif_api/http/http_method_enum.rb
75
+ - lib/moesif_api/http/http_request.rb
76
+ - lib/moesif_api/http/http_response.rb
77
+ - lib/moesif_api/http/unirest_client.rb
78
+ - lib/moesif_api/models/base_model.rb
79
+ - lib/moesif_api/models/event_model.rb
80
+ - lib/moesif_api/models/event_request_model.rb
81
+ - lib/moesif_api/models/event_response_model.rb
82
+ - lib/moesif_api/models/status_model.rb
83
+ - lib/moesif_api/moesif_api_client.rb
84
+ - test/controllers/controller_test_base.rb
85
+ - test/controllers/test_api_controller.rb
86
+ - test/http_response_catcher.rb
87
+ - test/test_helper.rb
88
+ homepage: https://moesif.com
89
+ licenses:
90
+ - MIT
91
+ metadata: {}
92
+ post_install_message:
93
+ rdoc_options: []
94
+ require_paths:
95
+ - lib
96
+ required_ruby_version: !ruby/object:Gem::Requirement
97
+ requirements:
98
+ - - ~>
99
+ - !ruby/object:Gem::Version
100
+ version: '2.0'
101
+ required_rubygems_version: !ruby/object:Gem::Requirement
102
+ requirements:
103
+ - - '>='
104
+ - !ruby/object:Gem::Version
105
+ version: '0'
106
+ requirements: []
107
+ rubyforge_project:
108
+ rubygems_version: 2.4.5
109
+ signing_key:
110
+ specification_version: 4
111
+ summary: moesif_api
112
+ test_files: []