esp_sdk 1.1.0 → 2.0.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (199) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +0 -2
  3. data/.rubocop.yml +53 -6
  4. data/.ruby-version +1 -1
  5. data/.travis.yml +8 -2
  6. data/Gemfile.lock +171 -0
  7. data/Guardfile +47 -0
  8. data/README.md +230 -5
  9. data/Rakefile +14 -1
  10. data/assets/logo.png +0 -0
  11. data/bin/esp_console +71 -0
  12. data/esp_sdk.gemspec +27 -18
  13. data/lib/esp/exceptions.rb +3 -0
  14. data/lib/esp/extensions/active_resource/formats/json_api_format.rb +105 -0
  15. data/lib/esp/extensions/active_resource/paginated_collection.rb +198 -0
  16. data/lib/esp/extensions/active_resource/validations.rb +45 -0
  17. data/lib/esp/resources/alert.rb +135 -0
  18. data/lib/esp/resources/cloud_trail_event.rb +45 -0
  19. data/lib/esp/resources/concerns/stat_totals.rb +79 -0
  20. data/lib/esp/resources/contact_request.rb +42 -0
  21. data/lib/esp/resources/custom_signature.rb +224 -0
  22. data/lib/esp/resources/dashboard.rb +31 -0
  23. data/lib/esp/resources/external_account.rb +89 -0
  24. data/lib/esp/resources/organization.rb +61 -0
  25. data/lib/esp/resources/region.rb +46 -0
  26. data/lib/esp/resources/report.rb +100 -0
  27. data/lib/esp/resources/resource.rb +66 -0
  28. data/lib/esp/resources/service.rb +31 -0
  29. data/lib/esp/resources/signature.rb +106 -0
  30. data/lib/esp/resources/stat.rb +124 -0
  31. data/lib/esp/resources/stat_custom_signature.rb +121 -0
  32. data/lib/esp/resources/stat_region.rb +121 -0
  33. data/lib/esp/resources/stat_service.rb +121 -0
  34. data/lib/esp/resources/stat_signature.rb +121 -0
  35. data/lib/esp/resources/sub_organization.rb +69 -0
  36. data/lib/esp/resources/suppression/region.rb +99 -0
  37. data/lib/esp/resources/suppression/signature.rb +107 -0
  38. data/lib/esp/resources/suppression/unique_identifier.rb +60 -0
  39. data/lib/esp/resources/suppression.rb +86 -0
  40. data/lib/esp/resources/tag.rb +45 -0
  41. data/lib/esp/resources/team.rb +79 -0
  42. data/lib/esp/resources/user.rb +46 -0
  43. data/lib/esp/version.rb +3 -0
  44. data/lib/esp.rb +95 -0
  45. data/lib/esp_sdk.rb +9 -45
  46. data/lib/tasks/rubocop.rake +2 -0
  47. data/lib/tasks/testing.rake +3 -0
  48. data/rdoc/ActiveResource/Formats.html +176 -0
  49. data/rdoc/ActiveResource/PaginatedCollection.html +910 -0
  50. data/rdoc/ActiveResource.html +180 -0
  51. data/rdoc/ESP/Alert.html +771 -0
  52. data/rdoc/ESP/CloudTrailEvent.html +375 -0
  53. data/rdoc/ESP/ContactRequest.html +366 -0
  54. data/rdoc/ESP/CustomSignature.html +746 -0
  55. data/rdoc/ESP/Dashboard.html +355 -0
  56. data/rdoc/ESP/ExternalAccount.html +565 -0
  57. data/rdoc/ESP/Organization.html +590 -0
  58. data/rdoc/ESP/Region.html +399 -0
  59. data/rdoc/ESP/Report.html +622 -0
  60. data/rdoc/ESP/Service.html +380 -0
  61. data/rdoc/ESP/Signature.html +555 -0
  62. data/rdoc/ESP/Stat.html +1778 -0
  63. data/rdoc/ESP/StatCustomSignature.html +1599 -0
  64. data/rdoc/ESP/StatRegion.html +1598 -0
  65. data/rdoc/ESP/StatService.html +1598 -0
  66. data/rdoc/ESP/StatSignature.html +1598 -0
  67. data/rdoc/ESP/SubOrganization.html +540 -0
  68. data/rdoc/ESP/Suppression/Region.html +454 -0
  69. data/rdoc/ESP/Suppression/Signature.html +470 -0
  70. data/rdoc/ESP/Suppression/UniqueIdentifier.html +417 -0
  71. data/rdoc/ESP/Suppression.html +649 -0
  72. data/rdoc/ESP/Tag.html +371 -0
  73. data/rdoc/ESP/Team.html +584 -0
  74. data/rdoc/ESP/User.html +483 -0
  75. data/rdoc/ESP.html +546 -0
  76. data/rdoc/README_md.html +501 -0
  77. data/rdoc/created.rid +30 -0
  78. data/rdoc/images/add.png +0 -0
  79. data/rdoc/images/arrow_up.png +0 -0
  80. data/rdoc/images/brick.png +0 -0
  81. data/rdoc/images/brick_link.png +0 -0
  82. data/rdoc/images/bug.png +0 -0
  83. data/rdoc/images/bullet_black.png +0 -0
  84. data/rdoc/images/bullet_toggle_minus.png +0 -0
  85. data/rdoc/images/bullet_toggle_plus.png +0 -0
  86. data/rdoc/images/date.png +0 -0
  87. data/rdoc/images/delete.png +0 -0
  88. data/rdoc/images/find.png +0 -0
  89. data/rdoc/images/loadingAnimation.gif +0 -0
  90. data/rdoc/images/macFFBgHack.png +0 -0
  91. data/rdoc/images/package.png +0 -0
  92. data/rdoc/images/page_green.png +0 -0
  93. data/rdoc/images/page_white_text.png +0 -0
  94. data/rdoc/images/page_white_width.png +0 -0
  95. data/rdoc/images/plugin.png +0 -0
  96. data/rdoc/images/ruby.png +0 -0
  97. data/rdoc/images/tag_blue.png +0 -0
  98. data/rdoc/images/tag_green.png +0 -0
  99. data/rdoc/images/transparent.png +0 -0
  100. data/rdoc/images/wrench.png +0 -0
  101. data/rdoc/images/wrench_orange.png +0 -0
  102. data/rdoc/images/zoom.png +0 -0
  103. data/rdoc/index.html +134 -0
  104. data/rdoc/js/darkfish.js +155 -0
  105. data/rdoc/js/jquery.js +4 -0
  106. data/rdoc/js/navigation.js +142 -0
  107. data/rdoc/js/search.js +94 -0
  108. data/rdoc/js/search_index.js +1 -0
  109. data/rdoc/js/searcher.js +228 -0
  110. data/rdoc/rdoc.css +595 -0
  111. data/rdoc/table_of_contents.html +927 -0
  112. data/test/esp/extensions/active_resource/formats/json_api_format_test.rb +109 -0
  113. data/test/esp/extensions/active_resource/paginated_collection_test.rb +435 -0
  114. data/test/esp/extensions/active_resource/validations_test.rb +59 -0
  115. data/test/esp/resources/alert_test.rb +263 -0
  116. data/test/esp/resources/cloud_trail_event_test.rb +98 -0
  117. data/test/esp/resources/contact_request_test.rb +73 -0
  118. data/test/esp/resources/custom_signature_test.rb +241 -0
  119. data/test/esp/resources/dashboard_test.rb +71 -0
  120. data/test/esp/resources/external_account_test.rb +125 -0
  121. data/test/esp/resources/organization_test.rb +175 -0
  122. data/test/esp/resources/region_test.rb +84 -0
  123. data/test/esp/resources/report_test.rb +180 -0
  124. data/test/esp/resources/resource_test.rb +183 -0
  125. data/test/esp/resources/service_test.rb +64 -0
  126. data/test/esp/resources/signature_test.rb +177 -0
  127. data/test/esp/resources/stat_custom_signature_test.rb +115 -0
  128. data/test/esp/resources/stat_region_test.rb +114 -0
  129. data/test/esp/resources/stat_service_test.rb +114 -0
  130. data/test/esp/resources/stat_signature_test.rb +115 -0
  131. data/test/esp/resources/stat_test.rb +159 -0
  132. data/test/esp/resources/sub_organization_test.rb +127 -0
  133. data/test/esp/resources/suppression/region_test.rb +115 -0
  134. data/test/esp/resources/suppression/signature_test.rb +117 -0
  135. data/test/esp/resources/suppression/unique_identifier_test.rb +79 -0
  136. data/test/esp/resources/suppression_test.rb +226 -0
  137. data/test/esp/resources/tag_test.rb +98 -0
  138. data/test/esp/resources/team_test.rb +140 -0
  139. data/test/esp/resources/user_test.rb +113 -0
  140. data/test/esp_test.rb +139 -0
  141. data/test/factories/alerts.rb +234 -0
  142. data/test/factories/cloud_trail_events.rb +16 -0
  143. data/test/factories/contact_requests.rb +14 -0
  144. data/test/factories/custom_signatures.rb +30 -0
  145. data/test/factories/dashboards.rb +91 -0
  146. data/test/factories/errors.rb +24 -0
  147. data/test/factories/external_accounts.rb +44 -0
  148. data/test/factories/organizations.rb +48 -0
  149. data/test/factories/regions.rb +9 -0
  150. data/test/factories/reports.rb +56 -0
  151. data/test/factories/services.rb +12 -0
  152. data/test/factories/signatures.rb +28 -0
  153. data/test/factories/stat_custom_signatures.rb +97 -0
  154. data/test/factories/stat_regions.rb +97 -0
  155. data/test/factories/stat_services.rb +97 -0
  156. data/test/factories/stat_signautures.rb +97 -0
  157. data/test/factories/stats.rb +129 -0
  158. data/test/factories/sub_organizations.rb +34 -0
  159. data/test/factories/suppression/regions.rb +90 -0
  160. data/test/factories/suppression/signatures.rb +117 -0
  161. data/test/factories/suppression/unique_identifiers.rb +111 -0
  162. data/test/factories/suppressions.rb +71 -0
  163. data/test/factories/tags.rb +12 -0
  164. data/test/factories/teams.rb +32 -0
  165. data/test/factories/users.rb +54 -0
  166. data/test/json_strategy.rb +25 -0
  167. data/test/test_helper.rb +44 -5
  168. metadata +387 -119
  169. data/bin/esp_repl +0 -60
  170. data/lib/esp_sdk/api.rb +0 -33
  171. data/lib/esp_sdk/client.rb +0 -62
  172. data/lib/esp_sdk/configure.rb +0 -40
  173. data/lib/esp_sdk/end_points/base.rb +0 -102
  174. data/lib/esp_sdk/end_points/contact_requests.rb +0 -6
  175. data/lib/esp_sdk/end_points/custom_signatures.rb +0 -41
  176. data/lib/esp_sdk/end_points/dashboard.rb +0 -35
  177. data/lib/esp_sdk/end_points/external_accounts.rb +0 -9
  178. data/lib/esp_sdk/end_points/organizations.rb +0 -6
  179. data/lib/esp_sdk/end_points/reports.rb +0 -6
  180. data/lib/esp_sdk/end_points/services.rb +0 -6
  181. data/lib/esp_sdk/end_points/signatures.rb +0 -39
  182. data/lib/esp_sdk/end_points/sub_organizations.rb +0 -6
  183. data/lib/esp_sdk/end_points/teams.rb +0 -6
  184. data/lib/esp_sdk/end_points/users.rb +0 -6
  185. data/lib/esp_sdk/exceptions.rb +0 -8
  186. data/lib/esp_sdk/extensions/rest_client/request.rb +0 -9
  187. data/lib/esp_sdk/repl.rb +0 -61
  188. data/lib/esp_sdk/version.rb +0 -3
  189. data/test/esp_sdk/api_test.rb +0 -36
  190. data/test/esp_sdk/client_test.rb +0 -129
  191. data/test/esp_sdk/configure_test.rb +0 -65
  192. data/test/esp_sdk/end_points/.keep +0 -0
  193. data/test/esp_sdk/end_points/base_test.rb +0 -230
  194. data/test/esp_sdk/end_points/custom_signatures_test.rb +0 -90
  195. data/test/esp_sdk/end_points/dashboard_test.rb +0 -55
  196. data/test/esp_sdk/end_points/external_accounts_test.rb +0 -20
  197. data/test/esp_sdk/end_points/signatures_test.rb +0 -83
  198. data/test/esp_sdk/exceptions_test.rb +0 -41
  199. data/test/esp_sdk_test.rb +0 -70
@@ -0,0 +1,109 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../../test_helper')
2
+
3
+ module ActiveResource
4
+ module Formats
5
+ class JsonAPIFormatTest < ActiveSupport::TestCase
6
+ context ActiveResource::Formats::JsonAPIFormat do
7
+ context '# decode' do
8
+ context 'with ESP::Suppression' do
9
+ should 'parse nested objects correctly' do
10
+ json = json(:alert)
11
+ parsed_json = JSON.parse(json)
12
+ stub_request(:get, %r{alerts/5.json*}).to_return(body: json)
13
+
14
+ alert = ESP::Alert.find(5)
15
+
16
+ assert_equal parsed_json['data']['attributes']['metadata']['abc'], alert.metadata.abc
17
+ end
18
+ end
19
+
20
+ context 'with ESP::Alert' do
21
+ should 'merge included objects' do
22
+ json = json_list(:alert, 1)
23
+ parsed_json = JSON.parse(json)
24
+ stub_request(:get, %r{reports/1/alerts.json*}).to_return(body: json)
25
+
26
+ alert = ESP::Alert.for_report(1).first
27
+
28
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'external_accounts' }['id'], alert.external_account.id
29
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'regions' }['id'], alert.region.id
30
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'signatures' }['id'], alert.signature.id
31
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'cloud_trail_events' }['id'], alert.cloud_trail_events.first.id
32
+ end
33
+
34
+ should 'assign foreign keys' do
35
+ json = json_list(:alert, 1)
36
+ parsed_json = JSON.parse(json)
37
+ stub_request(:get, %r{reports/1/alerts.json*}).to_return(body: json)
38
+
39
+ alert = ESP::Alert.for_report(1).first
40
+
41
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'external_accounts' }['id'], alert.external_account_id
42
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'regions' }['id'], alert.region_id
43
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'signatures' }['id'], alert.signature_id
44
+ assert_contains alert.cloud_trail_event_ids, parsed_json['included'].detect { |e| e['type'] == 'cloud_trail_events' }['id']
45
+
46
+ # nested objects too
47
+ assert_equal parsed_json['included'].detect { |e| e['type'] == 'external_accounts' }['relationships']['organization']['data']['id'], alert.external_account.organization_id
48
+ end
49
+ end
50
+ end
51
+
52
+ context 'live calls' do
53
+ setup do
54
+ skip "Make sure you run the live calls locally to ensure proper integration" if ENV['CI_SERVER']
55
+ WebMock.allow_net_connect!
56
+ end
57
+
58
+ teardown do
59
+ WebMock.disable_net_connect!
60
+ end
61
+ end
62
+ end
63
+
64
+ context ActiveResource::ConnectionError do
65
+ context "with ESP::Team" do
66
+ context '.initialize' do
67
+ should 'parse the response and return a descriptive error message' do
68
+ error_response = json(:error, :active_record)
69
+ response = Net::HTTPBadRequest.new('1.0', '200', '')
70
+ response.expects(:body).returns(error_response).at_least_once
71
+
72
+ error = ActiveResource::BadRequest.new(response)
73
+
74
+ assert_equal "Failed. Response code = 200. Response message = Name can't be blank Name is invalid Description can't be blank.", error.message
75
+ end
76
+
77
+ should 'have the generic message if there is not reponse body' do
78
+ error = ActiveResource::BadRequest.new('oh no')
79
+
80
+ assert_equal "Failed.", error.message
81
+ end
82
+ end
83
+ end
84
+
85
+ context 'live calls' do
86
+ setup do
87
+ skip "Make sure you run the live calls locally to ensure proper integration" if ENV['CI_SERVER']
88
+ WebMock.allow_net_connect!
89
+ end
90
+
91
+ teardown do
92
+ WebMock.disable_net_connect!
93
+ end
94
+
95
+ context "with ESP::Team" do
96
+ context '.initialize' do
97
+ should 'parse the error and return a descriptive error message' do
98
+ error = assert_raises ActiveResource::BadRequest do
99
+ ESP::Team.create
100
+ end
101
+ assert_equal 'Failed. Response code = 400. Response message = param is missing or the value is empty: attributes.', error.message
102
+ end
103
+ end
104
+ end
105
+ end
106
+ end
107
+ end
108
+ end
109
+ end
@@ -0,0 +1,435 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../test_helper')
2
+
3
+ module ActiveResource
4
+ class PaginatedCollectionTest < ActiveSupport::TestCase
5
+ context ActiveResource::PaginatedCollection do
6
+ context "with ESP::Alert" do
7
+ context '#parse_pagination_links' do
8
+ should 'not set the previous page or next page or last page when there is only 1 page' do
9
+ report = build(:report)
10
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 2, page: { number: 1, size: 20 }))
11
+
12
+ alerts = report.alerts
13
+
14
+ assert_equal '1', alerts.current_page_number
15
+ assert_nil alerts.next_page_number
16
+ assert_nil alerts.previous_page_number
17
+ assert_nil alerts.last_page_number
18
+ refute_predicate alerts, :next_page?
19
+ refute_predicate alerts, :previous_page?
20
+ assert_predicate alerts, :last_page?
21
+ end
22
+
23
+ should 'not set the previous page when on the first page' do
24
+ report = build(:report)
25
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 2, page: { number: 1, size: 1 }))
26
+
27
+ alerts = report.alerts
28
+
29
+ assert_equal '1', alerts.current_page_number
30
+ assert_equal '2', alerts.next_page_number
31
+ assert_nil alerts.previous_page_number
32
+ assert_equal '2', alerts.last_page_number
33
+ assert_predicate alerts, :next_page?
34
+ refute_predicate alerts, :previous_page?
35
+ refute_predicate alerts, :last_page?
36
+ end
37
+
38
+ should 'not set the next or last page page when on the last page' do
39
+ report = build(:report)
40
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 2, page: { number: 2, size: 1 }))
41
+
42
+ alerts = report.alerts
43
+
44
+ assert_equal '2', alerts.current_page_number
45
+ assert_nil alerts.next_page_number
46
+ assert_equal '1', alerts.previous_page_number
47
+ assert_nil alerts.last_page_number
48
+ refute_predicate alerts, :next_page?
49
+ assert_predicate alerts, :previous_page?
50
+ assert_predicate alerts, :last_page?
51
+ end
52
+
53
+ should 'set the next, last and previous page page when not on the first or last page' do
54
+ report = build(:report)
55
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 }))
56
+
57
+ alerts = report.alerts
58
+
59
+ assert_equal '2', alerts.current_page_number
60
+ assert_equal '3', alerts.next_page_number
61
+ assert_equal '1', alerts.previous_page_number
62
+ assert_equal '3', alerts.last_page_number
63
+ assert_predicate alerts, :next_page?
64
+ assert_predicate alerts, :previous_page?
65
+ refute_predicate alerts, :last_page?
66
+ end
67
+
68
+ should 'set page size on each link' do
69
+ report = build(:report)
70
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 }))
71
+
72
+ alerts = report.alerts
73
+
74
+ assert_equal '1', alerts.next_page_params['page']['size']
75
+ assert_equal '1', alerts.previous_page_params['page']['size']
76
+ assert_equal '1', alerts.last_page_params['page']['size']
77
+ end
78
+
79
+ should 'not set page size on previous link if on the last page' do
80
+ # The last page may not contain the full per page number of records, and will therefore come back with an incorrect size since the
81
+ # size is based on the collection size. This will mess up further calls to previous_page or first page so remove the size so it will bring back the default size.
82
+ report = build(:report)
83
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 2 }))
84
+
85
+ alerts = report.alerts
86
+
87
+ assert_equal false, alerts.previous_page_params['page'].key?('size')
88
+ end
89
+ end
90
+
91
+ context '#first_page' do
92
+ should 'call the api with the original url and the page number 1 param' do
93
+ report = build(:report)
94
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
95
+ alerts = report.alerts
96
+
97
+ page = alerts.first_page
98
+
99
+ assert_equal '1', page.current_page_number
100
+ assert_equal '2', alerts.current_page_number # original object is unchanged
101
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
102
+ if req.uri.query.present? # The first call will not have query params, only the second call
103
+ assert_equal "page[number]=1", URI.unescape(req.uri.query)
104
+ end
105
+ end
106
+ end
107
+
108
+ should 'not call the api and return self if already on the first page' do
109
+ report = build(:report)
110
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
111
+ alerts = report.alerts
112
+
113
+ page = alerts.first_page
114
+
115
+ assert_equal '1', page.current_page_number
116
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
117
+ assert_predicate req.uri.query, :blank? # It will only be called once to get the first page
118
+ end
119
+ end
120
+ end
121
+
122
+ context '#first_page!' do
123
+ should 'call the api with the original url and the page number 1 param and update itself' do
124
+ report = build(:report)
125
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
126
+ alerts = report.alerts
127
+
128
+ alerts.first_page!
129
+
130
+ assert_equal '1', alerts.current_page_number
131
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
132
+ if req.uri.query.present? # The first call will not have query params, only the second call
133
+ assert_equal "page[number]=1", URI.unescape(req.uri.query)
134
+ end
135
+ end
136
+ end
137
+ end
138
+
139
+ context '#previous_page' do
140
+ should 'call the api with the original url and the previous page number param' do
141
+ report = build(:report)
142
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
143
+ alerts = report.alerts
144
+
145
+ page = alerts.previous_page
146
+
147
+ assert_equal '1', page.current_page_number
148
+ assert_equal '2', alerts.current_page_number # original object is unchanged
149
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
150
+ if req.uri.query.present? # The first call will not have query params, only the second call
151
+ assert_equal "page[number]=1&page[size]=1", URI.unescape(req.uri.query)
152
+ end
153
+ end
154
+ end
155
+
156
+ should 'not call the api and return self if already on the first page' do
157
+ report = build(:report)
158
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
159
+ alerts = report.alerts
160
+
161
+ page = alerts.previous_page
162
+
163
+ assert_equal '1', page.current_page_number
164
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
165
+ assert_predicate req.uri.query, :blank? # It will only be called once to get the first page
166
+ end
167
+ end
168
+ end
169
+
170
+ context '#previous_page!' do
171
+ should 'call the api with the original url and the previous page number param and update itself' do
172
+ report = build(:report)
173
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 1, size: 1 }))
174
+ alerts = report.alerts
175
+
176
+ alerts.previous_page!
177
+
178
+ assert_equal '1', alerts.current_page_number
179
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
180
+ if req.uri.query.present? # The first call will not have query params, only the second call
181
+ assert_equal "page[number]=1&page[size]=1", URI.unescape(req.uri.query)
182
+ end
183
+ end
184
+ end
185
+ end
186
+
187
+ context '#next_page' do
188
+ should 'call the api with the original url and the next page number param' do
189
+ report = build(:report)
190
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
191
+ alerts = report.alerts
192
+
193
+ page = alerts.next_page
194
+
195
+ assert_equal '3', page.current_page_number
196
+ assert_equal '2', alerts.current_page_number # original object is unchanged
197
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
198
+ if req.uri.query.present? # The first call will not have query params, only the second call
199
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
200
+ end
201
+ end
202
+ end
203
+
204
+ should 'not call the api and return self if already on the last page' do
205
+ report = build(:report)
206
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
207
+ alerts = report.alerts
208
+
209
+ page = alerts.next_page
210
+
211
+ assert_equal '3', page.current_page_number
212
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
213
+ assert_predicate req.uri.query, :blank? # It will only be called once to get the first page
214
+ end
215
+ end
216
+ end
217
+
218
+ context '#next_page!' do
219
+ should 'call the api with the original url and the next page number param and update itself' do
220
+ report = build(:report)
221
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
222
+ alerts = report.alerts
223
+
224
+ alerts.next_page!
225
+
226
+ assert_equal '3', alerts.current_page_number
227
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
228
+ if req.uri.query.present? # The first call will not have query params, only the second call
229
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
230
+ end
231
+ end
232
+ end
233
+ end
234
+
235
+ context '#last_page' do
236
+ should 'call the api with the original url and the last page number param' do
237
+ report = build(:report)
238
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
239
+ alerts = report.alerts
240
+
241
+ page = alerts.last_page
242
+
243
+ assert_equal '3', page.current_page_number
244
+ assert_equal '2', alerts.current_page_number # original object is unchanged
245
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
246
+ if req.uri.query.present? # The first call will not have query params, only the second call
247
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
248
+ end
249
+ end
250
+ end
251
+
252
+ should 'not call the api and return self if already on the last page' do
253
+ report = build(:report)
254
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
255
+ alerts = report.alerts
256
+
257
+ page = alerts.last_page
258
+
259
+ assert_equal '3', page.current_page_number
260
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
261
+ assert_predicate req.uri.query, :blank? # It will only be called once to get the first page
262
+ end
263
+ end
264
+ end
265
+
266
+ context '#last_page!' do
267
+ should 'call the api with the original url and the last page number param and update itself' do
268
+ report = build(:report)
269
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
270
+ alerts = report.alerts
271
+
272
+ alerts.last_page!
273
+
274
+ assert_equal '3', alerts.current_page_number
275
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
276
+ if req.uri.query.present? # The first call will not have query params, only the second call
277
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
278
+ end
279
+ end
280
+ end
281
+ end
282
+
283
+ context '#page' do
284
+ should 'raise an error if the page number is not given' do
285
+ report = build(:report)
286
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
287
+ alerts = report.alerts
288
+
289
+ error = assert_raises ArgumentError do
290
+ alerts.page
291
+ end
292
+ assert_equal "You must supply a page number.", error.message
293
+ end
294
+
295
+ should 'raise an error if the page number is not a positive number' do
296
+ report = build(:report)
297
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
298
+ alerts = report.alerts
299
+
300
+ error = assert_raises ArgumentError do
301
+ alerts.page(0)
302
+ end
303
+ assert_equal "Page number cannot be less than 1.", error.message
304
+ end
305
+
306
+ should 'raise an error if the page number is greater than the last page number' do
307
+ report = build(:report)
308
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
309
+ alerts = report.alerts
310
+
311
+ error = assert_raises ArgumentError do
312
+ alerts.page(4)
313
+ end
314
+ assert_equal "Page number cannot be greater than the last page number.", error.message
315
+ end
316
+
317
+ should 'call the api with the original url and the page number param' do
318
+ report = build(:report)
319
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
320
+ alerts = report.alerts
321
+
322
+ page = alerts.page(3)
323
+
324
+ assert_equal '3', page.current_page_number
325
+ assert_equal '2', alerts.current_page_number # original object is unchanged
326
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
327
+ if req.uri.query.present? # The first call will not have query params, only the second call
328
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
329
+ end
330
+ end
331
+ end
332
+
333
+ should 'not call the api and return self if already on that page' do
334
+ report = build(:report)
335
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 }))
336
+ alerts = report.alerts
337
+
338
+ page = alerts.page(2)
339
+
340
+ assert_equal '2', page.current_page_number
341
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
342
+ assert_predicate req.uri.query, :blank? # It will only be called once to get the first page
343
+ end
344
+ end
345
+ end
346
+
347
+ context '#page!' do
348
+ should 'call the api with the original url and the page number 1 param and update itself' do
349
+ report = build(:report)
350
+ stub_request(:get, %r{reports/#{report.id}/alerts.json*}).to_return(body: json_list(:alert, 3, page: { number: 2, size: 1 })).then.to_return(body: json_list(:alert, 3, page: { number: 3, size: 1 }))
351
+ alerts = report.alerts
352
+
353
+ alerts.page!(3)
354
+
355
+ assert_equal '3', alerts.current_page_number
356
+ assert_requested(:get, %r{reports/#{report.id}/alerts.json*}) do |req|
357
+ if req.uri.query.present? # The first call will not have query params, only the second call
358
+ assert_equal "page[number]=3&page[size]=1", URI.unescape(req.uri.query)
359
+ end
360
+ end
361
+ end
362
+ end
363
+ end
364
+
365
+ context 'live calls' do
366
+ setup do
367
+ skip "Make sure you run the live calls locally to ensure proper integration" if ENV['CI_SERVER']
368
+ WebMock.allow_net_connect!
369
+ end
370
+
371
+ teardown do
372
+ WebMock.disable_net_connect!
373
+ end
374
+
375
+ should 'always return the correct page and update itself when using the ! methods' do
376
+ report = ESP::Report.last
377
+ alerts = report.alerts
378
+ last_page_number = alerts.last_page_number
379
+
380
+ assert_equal '1', alerts.current_page_number
381
+ first_id = alerts.first.id
382
+
383
+ alerts.next_page!
384
+ assert_equal '2', alerts.current_page_number
385
+ refute_equal first_id, alerts.first.id
386
+ first_id = alerts.first.id
387
+
388
+ alerts.last_page!
389
+ assert_equal last_page_number, alerts.current_page_number
390
+ refute_equal first_id, alerts.first.id
391
+ first_id = alerts.first.id
392
+
393
+ alerts.previous_page!
394
+ assert_equal alerts.last_page_number.to_i - 1, alerts.current_page_number.to_i
395
+ refute_equal first_id, alerts.first.id
396
+ assert_equal 20, alerts.count # make sure the size did not get messed up while on the last page
397
+ first_id = alerts.first.id
398
+
399
+ alerts.page!(4)
400
+ assert_equal '4', alerts.current_page_number
401
+ refute_equal first_id, alerts.first.id
402
+ end
403
+
404
+ should 'always return the correct page and when not using the ! methods' do
405
+ report = ESP::Report.last
406
+ alerts = report.alerts
407
+ last_page_number = alerts.last_page_number
408
+
409
+ assert_equal '1', alerts.current_page_number
410
+ first_id = alerts.first.id
411
+
412
+ page = alerts.next_page
413
+ assert_equal '2', page.current_page_number
414
+ refute_equal first_id, page.first.id
415
+ first_id = page.first.id
416
+
417
+ page = page.last_page
418
+ assert_equal last_page_number, page.current_page_number
419
+ refute_equal first_id, page.first.id
420
+ first_id = page.first.id
421
+
422
+ page = page.previous_page
423
+ assert_equal page.last_page_number.to_i - 1, page.current_page_number.to_i
424
+ refute_equal first_id, page.first.id
425
+ assert_equal 20, page.count # make sure the size did not get messed up while on the last page
426
+ first_id = page.first.id
427
+
428
+ page = alerts.page(4)
429
+ assert_equal '4', page.current_page_number
430
+ refute_equal first_id, page.first.id
431
+ end
432
+ end
433
+ end
434
+ end
435
+ end
@@ -0,0 +1,59 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../test_helper')
2
+
3
+ module ActiveResource
4
+ class ValidationsTest < ActiveSupport::TestCase
5
+ context ActiveResource::Validations do
6
+ context "with ESP::Team" do
7
+ context '#load_remote_errors' do
8
+ should 'should parse an active record response and put error messages in the errors object' do
9
+ error = ActiveResource::ResourceInvalid.new('') # ResourceInvalid gets caught by the create method.
10
+ error_response = json(:error, :active_record)
11
+ response = mock(body: error_response)
12
+ error.expects(:response).returns(response)
13
+ ActiveResource::Connection.any_instance.expects(:post).raises(error)
14
+ stub_request(:post, /teams.json*/).to_return(body: json_list(:alert, 2))
15
+
16
+ team = ESP::Team.create
17
+
18
+ assert_contains team.errors.full_messages, "Name can't be blank"
19
+ assert_contains team.errors.full_messages, "Name is invalid"
20
+ assert_contains team.errors.full_messages, "Description can't be blank"
21
+ end
22
+
23
+ should 'should parse a non active record response and put error messages in the errors object' do
24
+ error = ActiveResource::ResourceInvalid.new('') # ResourceInvalid gets caught by the create method.
25
+ error_response = json(:error)
26
+ response = mock(body: error_response)
27
+ error.expects(:response).returns(response)
28
+ ActiveResource::Connection.any_instance.expects(:post).raises(error)
29
+ stub_request(:post, /teams.json*/).to_return(body: json_list(:alert, 2))
30
+
31
+ team = ESP::Team.create
32
+
33
+ assert_contains team.errors.full_messages, "Access Denied"
34
+ end
35
+ end
36
+ end
37
+
38
+ context 'live calls' do
39
+ setup do
40
+ skip "Make sure you run the live calls locally to ensure proper integration" if ENV['CI_SERVER']
41
+ WebMock.allow_net_connect!
42
+ end
43
+
44
+ teardown do
45
+ WebMock.disable_net_connect!
46
+ end
47
+
48
+ context "#load_remote_errors" do
49
+ should 'should parse the response and put error messages in the errors object' do
50
+ team = ESP::Team.create(name: 'bob')
51
+
52
+ assert_contains team.errors.full_messages, "Organization can't be blank"
53
+ assert_contains team.errors.full_messages, "Organization can't be blank"
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end