flapjack 1.6.0 → 2.0.0b1

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 (301) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +4 -6
  3. data/.gitmodules +1 -1
  4. data/.rspec +1 -1
  5. data/.ruby-version +1 -1
  6. data/.travis.yml +12 -13
  7. data/CHANGELOG.md +2 -9
  8. data/CONTRIBUTING.md +7 -2
  9. data/Gemfile +4 -13
  10. data/LICENCE +1 -0
  11. data/README.md +8 -2
  12. data/Rakefile +2 -2
  13. data/bin/flapjack +3 -12
  14. data/build.sh +4 -2
  15. data/etc/flapjack_config.toml.example +273 -0
  16. data/features/ack_after_sched_maint.feature +18 -21
  17. data/features/cli.feature +11 -71
  18. data/features/cli_flapjack-feed-events.feature +14 -15
  19. data/features/cli_flapjack-nagios-receiver.feature +12 -41
  20. data/features/cli_flapper.feature +12 -41
  21. data/features/cli_purge.feature +5 -6
  22. data/features/cli_receive-events.feature +6 -7
  23. data/features/cli_simulate-failed-check.feature +5 -6
  24. data/features/events.feature +206 -181
  25. data/features/events_check_names.feature +4 -7
  26. data/features/notification_rules.feature +144 -223
  27. data/features/notifications.feature +65 -57
  28. data/features/rollup.feature +45 -47
  29. data/features/steps/cli_steps.rb +4 -5
  30. data/features/steps/events_steps.rb +163 -373
  31. data/features/steps/notifications_steps.rb +408 -264
  32. data/features/steps/packaging-lintian_steps.rb +0 -4
  33. data/features/steps/time_travel_steps.rb +0 -26
  34. data/features/support/daemons.rb +6 -31
  35. data/features/support/env.rb +65 -74
  36. data/flapjack.gemspec +22 -24
  37. data/lib/flapjack.rb +14 -7
  38. data/lib/flapjack/cli/flapper.rb +74 -173
  39. data/lib/flapjack/cli/maintenance.rb +278 -109
  40. data/lib/flapjack/cli/migrate.rb +950 -0
  41. data/lib/flapjack/cli/purge.rb +19 -22
  42. data/lib/flapjack/cli/receiver.rb +150 -326
  43. data/lib/flapjack/cli/server.rb +8 -235
  44. data/lib/flapjack/cli/simulate.rb +42 -57
  45. data/lib/flapjack/configuration.rb +51 -37
  46. data/lib/flapjack/coordinator.rb +138 -129
  47. data/lib/flapjack/data/acknowledgement.rb +177 -0
  48. data/lib/flapjack/data/alert.rb +97 -158
  49. data/lib/flapjack/data/check.rb +611 -0
  50. data/lib/flapjack/data/condition.rb +70 -0
  51. data/lib/flapjack/data/contact.rb +226 -456
  52. data/lib/flapjack/data/event.rb +96 -184
  53. data/lib/flapjack/data/extensions/associations.rb +59 -0
  54. data/lib/flapjack/data/extensions/short_name.rb +25 -0
  55. data/lib/flapjack/data/medium.rb +428 -0
  56. data/lib/flapjack/data/metrics.rb +194 -0
  57. data/lib/flapjack/data/notification.rb +22 -281
  58. data/lib/flapjack/data/rule.rb +473 -0
  59. data/lib/flapjack/data/scheduled_maintenance.rb +244 -0
  60. data/lib/flapjack/data/state.rb +221 -0
  61. data/lib/flapjack/data/statistic.rb +112 -0
  62. data/lib/flapjack/data/tag.rb +277 -0
  63. data/lib/flapjack/data/test_notification.rb +182 -0
  64. data/lib/flapjack/data/unscheduled_maintenance.rb +159 -0
  65. data/lib/flapjack/data/validators/id_validator.rb +20 -0
  66. data/lib/flapjack/exceptions.rb +6 -0
  67. data/lib/flapjack/filters/acknowledgement.rb +23 -16
  68. data/lib/flapjack/filters/base.rb +0 -5
  69. data/lib/flapjack/filters/delays.rb +53 -43
  70. data/lib/flapjack/filters/ok.rb +23 -14
  71. data/lib/flapjack/filters/scheduled_maintenance.rb +3 -3
  72. data/lib/flapjack/filters/unscheduled_maintenance.rb +12 -3
  73. data/lib/flapjack/gateways/aws_sns.rb +65 -49
  74. data/lib/flapjack/gateways/aws_sns/alert.text.erb +2 -2
  75. data/lib/flapjack/gateways/aws_sns/alert_subject.text.erb +2 -2
  76. data/lib/flapjack/gateways/aws_sns/rollup_subject.text.erb +1 -1
  77. data/lib/flapjack/gateways/email.rb +107 -90
  78. data/lib/flapjack/gateways/email/alert.html.erb +19 -18
  79. data/lib/flapjack/gateways/email/alert.text.erb +20 -14
  80. data/lib/flapjack/gateways/email/alert_subject.text.erb +2 -1
  81. data/lib/flapjack/gateways/email/rollup.html.erb +14 -13
  82. data/lib/flapjack/gateways/email/rollup.text.erb +13 -10
  83. data/lib/flapjack/gateways/jabber.rb +679 -671
  84. data/lib/flapjack/gateways/jabber/alert.text.erb +9 -6
  85. data/lib/flapjack/gateways/jsonapi.rb +164 -350
  86. data/lib/flapjack/gateways/jsonapi/data/join_descriptor.rb +44 -0
  87. data/lib/flapjack/gateways/jsonapi/data/method_descriptor.rb +21 -0
  88. data/lib/flapjack/gateways/jsonapi/helpers/headers.rb +63 -0
  89. data/lib/flapjack/gateways/jsonapi/helpers/miscellaneous.rb +136 -0
  90. data/lib/flapjack/gateways/jsonapi/helpers/resources.rb +227 -0
  91. data/lib/flapjack/gateways/jsonapi/helpers/serialiser.rb +313 -0
  92. data/lib/flapjack/gateways/jsonapi/helpers/swagger_docs.rb +322 -0
  93. data/lib/flapjack/gateways/jsonapi/methods/association_delete.rb +115 -0
  94. data/lib/flapjack/gateways/jsonapi/methods/association_get.rb +288 -0
  95. data/lib/flapjack/gateways/jsonapi/methods/association_patch.rb +178 -0
  96. data/lib/flapjack/gateways/jsonapi/methods/association_post.rb +116 -0
  97. data/lib/flapjack/gateways/jsonapi/methods/metrics.rb +71 -0
  98. data/lib/flapjack/gateways/jsonapi/methods/resource_delete.rb +119 -0
  99. data/lib/flapjack/gateways/jsonapi/methods/resource_get.rb +186 -0
  100. data/lib/flapjack/gateways/jsonapi/methods/resource_patch.rb +239 -0
  101. data/lib/flapjack/gateways/jsonapi/methods/resource_post.rb +197 -0
  102. data/lib/flapjack/gateways/jsonapi/middleware/array_param_fixer.rb +27 -0
  103. data/lib/flapjack/gateways/jsonapi/{rack → middleware}/json_params_parser.rb +7 -6
  104. data/lib/flapjack/gateways/jsonapi/middleware/request_timestamp.rb +18 -0
  105. data/lib/flapjack/gateways/oobetet.rb +222 -170
  106. data/lib/flapjack/gateways/pager_duty.rb +388 -0
  107. data/lib/flapjack/gateways/pager_duty/alert.text.erb +13 -0
  108. data/lib/flapjack/gateways/slack.rb +56 -48
  109. data/lib/flapjack/gateways/slack/alert.text.erb +1 -1
  110. data/lib/flapjack/gateways/slack/rollup.text.erb +1 -1
  111. data/lib/flapjack/gateways/sms_aspsms.rb +155 -0
  112. data/lib/flapjack/gateways/sms_aspsms/alert.text.erb +7 -0
  113. data/lib/flapjack/gateways/sms_aspsms/rollup.text.erb +2 -0
  114. data/lib/flapjack/gateways/sms_messagenet.rb +77 -57
  115. data/lib/flapjack/gateways/sms_messagenet/alert.text.erb +3 -2
  116. data/lib/flapjack/gateways/sms_nexmo.rb +53 -51
  117. data/lib/flapjack/gateways/sms_nexmo/alert.text.erb +2 -2
  118. data/lib/flapjack/gateways/sms_nexmo/rollup.text.erb +1 -1
  119. data/lib/flapjack/gateways/sms_twilio.rb +79 -62
  120. data/lib/flapjack/gateways/sms_twilio/alert.text.erb +3 -2
  121. data/lib/flapjack/gateways/web.rb +437 -345
  122. data/lib/flapjack/gateways/web/middleware/request_timestamp.rb +18 -0
  123. data/lib/flapjack/gateways/web/public/css/bootstrap.css +3793 -4340
  124. data/lib/flapjack/gateways/web/public/css/bootstrap.css.map +1 -0
  125. data/lib/flapjack/gateways/web/public/fonts/glyphicons-halflings-regular.eot +0 -0
  126. data/lib/flapjack/gateways/web/public/fonts/glyphicons-halflings-regular.svg +273 -214
  127. data/lib/flapjack/gateways/web/public/fonts/glyphicons-halflings-regular.ttf +0 -0
  128. data/lib/flapjack/gateways/web/public/fonts/glyphicons-halflings-regular.woff +0 -0
  129. data/lib/flapjack/gateways/web/public/fonts/glyphicons-halflings-regular.woff2 +0 -0
  130. data/lib/flapjack/gateways/web/public/js/bootstrap.js +1637 -1607
  131. data/lib/flapjack/gateways/web/public/js/self_stats.js +1 -2
  132. data/lib/flapjack/gateways/web/views/_pagination.html.erb +19 -0
  133. data/lib/flapjack/gateways/web/views/check.html.erb +159 -121
  134. data/lib/flapjack/gateways/web/views/checks.html.erb +82 -41
  135. data/lib/flapjack/gateways/web/views/contact.html.erb +59 -71
  136. data/lib/flapjack/gateways/web/views/contacts.html.erb +32 -8
  137. data/lib/flapjack/gateways/web/views/index.html.erb +2 -2
  138. data/lib/flapjack/gateways/web/views/{layout.erb → layout.html.erb} +7 -23
  139. data/lib/flapjack/gateways/web/views/self_stats.html.erb +32 -33
  140. data/lib/flapjack/gateways/web/views/tag.html.erb +32 -0
  141. data/lib/flapjack/gateways/web/views/tags.html.erb +51 -0
  142. data/lib/flapjack/logger.rb +34 -3
  143. data/lib/flapjack/notifier.rb +180 -112
  144. data/lib/flapjack/patches.rb +8 -63
  145. data/lib/flapjack/pikelet.rb +185 -143
  146. data/lib/flapjack/processor.rb +323 -191
  147. data/lib/flapjack/record_queue.rb +33 -0
  148. data/lib/flapjack/redis_proxy.rb +66 -0
  149. data/lib/flapjack/utility.rb +21 -15
  150. data/lib/flapjack/version.rb +2 -1
  151. data/libexec/httpbroker.go +218 -14
  152. data/libexec/oneoff.go +13 -10
  153. data/spec/lib/flapjack/configuration_spec.rb +286 -0
  154. data/spec/lib/flapjack/coordinator_spec.rb +103 -157
  155. data/spec/lib/flapjack/data/check_spec.rb +175 -0
  156. data/spec/lib/flapjack/data/contact_spec.rb +26 -349
  157. data/spec/lib/flapjack/data/event_spec.rb +76 -291
  158. data/spec/lib/flapjack/data/medium_spec.rb +19 -0
  159. data/spec/lib/flapjack/data/rule_spec.rb +43 -0
  160. data/spec/lib/flapjack/data/scheduled_maintenance_spec.rb +976 -0
  161. data/spec/lib/flapjack/data/unscheduled_maintenance_spec.rb +34 -0
  162. data/spec/lib/flapjack/gateways/aws_sns_spec.rb +111 -60
  163. data/spec/lib/flapjack/gateways/email_spec.rb +194 -161
  164. data/spec/lib/flapjack/gateways/jabber_spec.rb +961 -162
  165. data/spec/lib/flapjack/gateways/jsonapi/methods/check_links_spec.rb +155 -0
  166. data/spec/lib/flapjack/gateways/jsonapi/methods/checks_spec.rb +426 -0
  167. data/spec/lib/flapjack/gateways/jsonapi/methods/contact_links_spec.rb +217 -0
  168. data/spec/lib/flapjack/gateways/jsonapi/methods/contacts_spec.rb +425 -0
  169. data/spec/lib/flapjack/gateways/jsonapi/methods/events_spec.rb +271 -0
  170. data/spec/lib/flapjack/gateways/jsonapi/methods/media_spec.rb +257 -0
  171. data/spec/lib/flapjack/gateways/jsonapi/methods/medium_links_spec.rb +163 -0
  172. data/spec/lib/flapjack/gateways/jsonapi/methods/metrics_spec.rb +8 -0
  173. data/spec/lib/flapjack/gateways/jsonapi/methods/rule_links_spec.rb +212 -0
  174. data/spec/lib/flapjack/gateways/jsonapi/methods/rules_spec.rb +289 -0
  175. data/spec/lib/flapjack/gateways/jsonapi/methods/scheduled_maintenance_links_spec.rb +49 -0
  176. data/spec/lib/flapjack/gateways/jsonapi/methods/scheduled_maintenances_spec.rb +242 -0
  177. data/spec/lib/flapjack/gateways/jsonapi/methods/tag_links_spec.rb +274 -0
  178. data/spec/lib/flapjack/gateways/jsonapi/methods/tags_spec.rb +302 -0
  179. data/spec/lib/flapjack/gateways/jsonapi/methods/unscheduled_maintenance_links_spec.rb +49 -0
  180. data/spec/lib/flapjack/gateways/jsonapi/methods/unscheduled_maintenances_spec.rb +339 -0
  181. data/spec/lib/flapjack/gateways/jsonapi_spec.rb +1 -1
  182. data/spec/lib/flapjack/gateways/oobetet_spec.rb +151 -79
  183. data/spec/lib/flapjack/gateways/pager_duty_spec.rb +353 -0
  184. data/spec/lib/flapjack/gateways/slack_spec.rb +53 -53
  185. data/spec/lib/flapjack/gateways/sms_aspsms_spec.rb +106 -0
  186. data/spec/lib/flapjack/gateways/sms_messagenet_spec.rb +111 -54
  187. data/spec/lib/flapjack/gateways/sms_nexmo_spec.rb +50 -51
  188. data/spec/lib/flapjack/gateways/sms_twilio_spec.rb +108 -48
  189. data/spec/lib/flapjack/gateways/web_spec.rb +144 -216
  190. data/spec/lib/flapjack/notifier_spec.rb +132 -1
  191. data/spec/lib/flapjack/pikelet_spec.rb +111 -50
  192. data/spec/lib/flapjack/processor_spec.rb +210 -40
  193. data/spec/lib/flapjack/redis_proxy_spec.rb +45 -0
  194. data/spec/lib/flapjack/utility_spec.rb +11 -15
  195. data/spec/service_consumers/fixture_data.rb +547 -0
  196. data/spec/service_consumers/pact_helper.rb +21 -32
  197. data/spec/service_consumers/pacts/flapjack-diner_v2.0.json +4652 -0
  198. data/spec/service_consumers/provider_states_for_flapjack-diner.rb +279 -322
  199. data/spec/service_consumers/provider_support.rb +8 -0
  200. data/spec/spec_helper.rb +34 -44
  201. data/spec/support/erb_view_helper.rb +1 -1
  202. data/spec/support/factories.rb +58 -0
  203. data/spec/support/jsonapi_helper.rb +15 -26
  204. data/spec/support/mock_logger.rb +43 -0
  205. data/spec/support/xmpp_comparable.rb +24 -0
  206. data/src/flapjack/transport_test.go +30 -1
  207. data/tasks/dump_keys.rake +82 -0
  208. data/tasks/events.rake +7 -7
  209. data/tasks/support/flapjack_config_benchmark.toml +28 -0
  210. data/tasks/support/flapjack_config_benchmark.yaml +0 -2
  211. metadata +175 -222
  212. data/Guardfile +0 -14
  213. data/etc/flapjack_config.yaml.example +0 -477
  214. data/features/cli_flapjack-populator.feature +0 -90
  215. data/features/support/silent_system.rb +0 -4
  216. data/lib/flapjack/cli/import.rb +0 -108
  217. data/lib/flapjack/data/entity.rb +0 -652
  218. data/lib/flapjack/data/entity_check.rb +0 -1044
  219. data/lib/flapjack/data/message.rb +0 -56
  220. data/lib/flapjack/data/migration.rb +0 -234
  221. data/lib/flapjack/data/notification_rule.rb +0 -425
  222. data/lib/flapjack/data/semaphore.rb +0 -44
  223. data/lib/flapjack/data/tagged.rb +0 -48
  224. data/lib/flapjack/gateways/jsonapi/check_methods.rb +0 -206
  225. data/lib/flapjack/gateways/jsonapi/check_presenter.rb +0 -221
  226. data/lib/flapjack/gateways/jsonapi/contact_methods.rb +0 -186
  227. data/lib/flapjack/gateways/jsonapi/entity_methods.rb +0 -223
  228. data/lib/flapjack/gateways/jsonapi/medium_methods.rb +0 -185
  229. data/lib/flapjack/gateways/jsonapi/metrics_methods.rb +0 -132
  230. data/lib/flapjack/gateways/jsonapi/notification_rule_methods.rb +0 -141
  231. data/lib/flapjack/gateways/jsonapi/pagerduty_credential_methods.rb +0 -139
  232. data/lib/flapjack/gateways/jsonapi/report_methods.rb +0 -146
  233. data/lib/flapjack/gateways/pagerduty.rb +0 -318
  234. data/lib/flapjack/gateways/pagerduty/alert.text.erb +0 -10
  235. data/lib/flapjack/gateways/web/public/css/select2-bootstrap.css +0 -87
  236. data/lib/flapjack/gateways/web/public/css/select2.css +0 -615
  237. data/lib/flapjack/gateways/web/public/css/tablesort.css +0 -67
  238. data/lib/flapjack/gateways/web/public/img/select2-spinner.gif +0 -0
  239. data/lib/flapjack/gateways/web/public/img/select2.png +0 -0
  240. data/lib/flapjack/gateways/web/public/img/select2x2.png +0 -0
  241. data/lib/flapjack/gateways/web/public/js/backbone.js +0 -1581
  242. data/lib/flapjack/gateways/web/public/js/backbone.jsonapi.js +0 -322
  243. data/lib/flapjack/gateways/web/public/js/flapjack.js +0 -82
  244. data/lib/flapjack/gateways/web/public/js/jquery.tablesorter.js +0 -1640
  245. data/lib/flapjack/gateways/web/public/js/jquery.tablesorter.widgets.js +0 -1390
  246. data/lib/flapjack/gateways/web/public/js/modules/contact.js +0 -520
  247. data/lib/flapjack/gateways/web/public/js/modules/entity.js +0 -28
  248. data/lib/flapjack/gateways/web/public/js/modules/medium.js +0 -40
  249. data/lib/flapjack/gateways/web/public/js/select2.js +0 -3397
  250. data/lib/flapjack/gateways/web/public/js/tablesort.js +0 -44
  251. data/lib/flapjack/gateways/web/public/js/underscore.js +0 -1276
  252. data/lib/flapjack/gateways/web/views/edit_contacts.html.erb +0 -173
  253. data/lib/flapjack/gateways/web/views/entities.html.erb +0 -30
  254. data/lib/flapjack/gateways/web/views/entity.html.erb +0 -51
  255. data/lib/flapjack/rack_logger.rb +0 -47
  256. data/lib/flapjack/redis_pool.rb +0 -42
  257. data/spec/lib/flapjack/data/entity_check_spec.rb +0 -1418
  258. data/spec/lib/flapjack/data/entity_spec.rb +0 -872
  259. data/spec/lib/flapjack/data/message_spec.rb +0 -30
  260. data/spec/lib/flapjack/data/migration_spec.rb +0 -104
  261. data/spec/lib/flapjack/data/notification_rule_spec.rb +0 -232
  262. data/spec/lib/flapjack/data/notification_spec.rb +0 -53
  263. data/spec/lib/flapjack/data/semaphore_spec.rb +0 -24
  264. data/spec/lib/flapjack/filters/acknowledgement_spec.rb +0 -6
  265. data/spec/lib/flapjack/filters/delays_spec.rb +0 -6
  266. data/spec/lib/flapjack/filters/ok_spec.rb +0 -6
  267. data/spec/lib/flapjack/filters/scheduled_maintenance_spec.rb +0 -6
  268. data/spec/lib/flapjack/filters/unscheduled_maintenance_spec.rb +0 -6
  269. data/spec/lib/flapjack/gateways/jsonapi/check_methods_spec.rb +0 -315
  270. data/spec/lib/flapjack/gateways/jsonapi/check_presenter_spec.rb +0 -223
  271. data/spec/lib/flapjack/gateways/jsonapi/contact_methods_spec.rb +0 -131
  272. data/spec/lib/flapjack/gateways/jsonapi/entity_methods_spec.rb +0 -389
  273. data/spec/lib/flapjack/gateways/jsonapi/medium_methods_spec.rb +0 -231
  274. data/spec/lib/flapjack/gateways/jsonapi/notification_rule_methods_spec.rb +0 -169
  275. data/spec/lib/flapjack/gateways/jsonapi/pagerduty_credential_methods_spec.rb +0 -114
  276. data/spec/lib/flapjack/gateways/jsonapi/report_methods_spec.rb +0 -590
  277. data/spec/lib/flapjack/gateways/pagerduty_spec.rb +0 -249
  278. data/spec/lib/flapjack/gateways/web/views/check.html.erb_spec.rb +0 -21
  279. data/spec/lib/flapjack/gateways/web/views/contact.html.erb_spec.rb +0 -24
  280. data/spec/lib/flapjack/gateways/web/views/index.html.erb_spec.rb +0 -16
  281. data/spec/lib/flapjack/redis_pool_spec.rb +0 -29
  282. data/spec/service_consumers/pacts/flapjack-diner_v1.0.json +0 -4702
  283. data/tasks/entities.rake +0 -151
  284. data/tasks/profile.rake +0 -282
  285. data/tmp/acknowledge.rb +0 -13
  286. data/tmp/create_config_yaml.rb +0 -16
  287. data/tmp/create_event_ok.rb +0 -30
  288. data/tmp/create_event_unknown.rb +0 -30
  289. data/tmp/create_events_failure.rb +0 -34
  290. data/tmp/create_events_ok.rb +0 -32
  291. data/tmp/create_events_ok_fail_ack_ok.rb +0 -53
  292. data/tmp/create_events_ok_failure.rb +0 -41
  293. data/tmp/create_events_ok_failure_ack.rb +0 -53
  294. data/tmp/dummy_contacts.json +0 -43
  295. data/tmp/dummy_entities.json +0 -37
  296. data/tmp/generate_nagios_test_hosts.rb +0 -16
  297. data/tmp/notification_rules.rb +0 -73
  298. data/tmp/parse_config_yaml.rb +0 -7
  299. data/tmp/redis_find_spurious_unknown_states.rb +0 -52
  300. data/tmp/test_json_post.rb +0 -19
  301. data/tmp/test_notification_rules_api.rb +0 -171
@@ -1,35 +1,31 @@
1
1
  #!/usr/bin/env ruby
2
2
 
3
- require 'flapjack'
4
-
5
- require 'flapjack/data/migration'
3
+ require 'flapjack/redis_proxy'
6
4
 
7
5
  module Flapjack
8
6
  module Data
9
7
  class Event
10
8
 
11
- attr_accessor :counter, :id_hash, :tags
9
+ attr_accessor :counter, :id_hash
12
10
 
13
- attr_reader :check, :summary, :details, :acknowledgement_id, :perfdata,
14
- :initial_failure_delay, :repeat_failure_delay
11
+ attr_reader :id, :summary, :details, :acknowledgement_id, :perfdata
15
12
 
16
- REQUIRED_KEYS = ['type', 'state', 'entity', 'check']
17
- OPTIONAL_KEYS = ['time', 'summary', 'details', 'acknowledgement_id',
18
- 'duration', 'tags', 'perfdata', 'initial_failure_delay',
19
- 'repeat_failure_delay']
13
+ # type was a required key in v1, but is superfluous
14
+ # tags are now ignored, tags on the checks are used for rule matching
15
+ REQUIRED_KEYS = %w(state check)
16
+ OPTIONAL_KEYS = %w(entity time initial_failure_delay
17
+ repeat_failure_delay summary details acknowledgement_id duration tags
18
+ perfdata type)
20
19
 
21
20
  VALIDATIONS = {
22
- proc {|e| e['type'].is_a?(String) &&
23
- ['service', 'action'].include?(e['type'].downcase) } =>
24
- "type must be either 'service' or 'action'",
25
-
26
21
  proc {|e| e['state'].is_a?(String) &&
27
22
  ['ok', 'warning', 'critical', 'unknown', 'acknowledgement',
28
- 'test_notifications'].include?(e['state'].downcase) } =>
23
+ 'test_notifications'].include?(e['state'].downcase) ||
24
+ !(e['state'] =~ /\Atest_notifications(?:\s+#{Flapjack::Data::Condition.unhealthy.keys.join('|')})?\z/).nil? } =>
29
25
  "state must be one of 'ok', 'warning', 'critical', 'unknown', " +
30
- "'acknowledgement' or 'test_notifications'",
26
+ "'acknowledgement', 'test_notifications', or 'test_notifications [problem]' ",
31
27
 
32
- proc {|e| e['entity'].is_a?(String) } =>
28
+ proc {|e| e['entity'].nil? || e['entity'].is_a?(String) } =>
33
29
  "entity must be a string",
34
30
 
35
31
  proc {|e| e['check'].is_a?(String) } =>
@@ -70,93 +66,25 @@ module Flapjack
70
66
  "duration must be a positive integer, or a string castable to one",
71
67
 
72
68
  proc {|e| e['tags'].nil? ||
73
- (e['tags'].is_a?(Array) &&
74
- e['tags'].all? {|tag| tag.is_a?(String)}) } =>
69
+ (e['tags'].is_a?(Array) &&
70
+ e['tags'].all? {|tag| tag.is_a?(String)}) } =>
75
71
  "tags must be an array of strings",
76
72
  }
77
73
 
78
- # Helper method for getting the next event.
79
- #
80
- # Has a blocking and non-blocking method signature.
81
- #
82
- # Calling next with :block => true, we wait indefinitely for events coming
83
- # from other systems. This is the default behaviour.
84
- #
85
- # Calling next with :block => false, will return a nil if there are no
86
- # events on the queue.
87
- def self.next(queue, opts = {})
88
- raise "Redis connection not set" unless redis = opts[:redis]
89
-
90
- defaults = { :block => true,
91
- :archive_events => false,
92
- :events_archive_maxage => (3 * 60 * 60) }
93
- options = defaults.merge(opts)
94
-
95
- archive_dest = nil
96
- base_time_str = Time.now.utc.strftime("%Y%m%d%H")
97
-
98
- if options[:archive_events]
99
- archive_dest = "events_archive:#{base_time_str}"
100
- unless @previous_base_time_str == base_time_str
101
- Flapjack::Data::Migration.purge_expired_archive_index(:redis => redis)
102
- end
103
- @previous_base_time_str = base_time_str
104
- if options[:block]
105
- raw = redis.brpoplpush(queue, archive_dest, 0)
106
- else
107
- raw = redis.rpoplpush(queue, archive_dest)
108
- return unless raw
109
- end
110
- redis.sadd("known_events_archive_keys", archive_dest)
111
- elsif options[:block]
112
- raw = redis.brpop(queue, 0)[1]
113
- else
114
- raw = redis.rpop(queue)
115
- return unless raw
116
- end
117
- parsed = parse_and_validate(raw, :logger => options[:logger])
118
- if parsed.nil?
119
- # either bad json or invalid data -- in either case we'll
120
- # store the raw data in a rejected list
121
- rejected_dest = "events_rejected:#{base_time_str}"
122
- if options[:archive_events]
123
- redis.multi do |multi|
124
- multi.lrem(archive_dest, 1, raw)
125
- multi.lpush(rejected_dest, raw)
126
- end
127
- redis.expire(archive_dest, options[:events_archive_maxage])
128
- else
129
- redis.lpush(rejected_dest, raw)
130
- end
131
- return
132
- elsif options[:archive_events]
133
- redis.expire(archive_dest, options[:events_archive_maxage])
134
- end
135
- self.new(parsed)
136
- end
137
-
138
74
  def self.parse_and_validate(raw, opts = {})
139
75
  errors = []
140
- if parsed = ::Flapjack.load_json(raw)
141
- return if 'noop'.eql?(parsed['type'])
76
+ if parsed = Flapjack.load_json(raw)
142
77
  if parsed.is_a?(Hash)
143
78
  errors = validation_errors_for_hash(parsed, opts)
144
79
  else
145
80
  errors << "Event must be a JSON hash, see http://flapjack.io/docs/1.0/development/DATA_STRUCTURES#event-queue"
146
81
  end
147
- return parsed if errors.empty?
148
- end
149
-
150
- if opts[:logger]
151
- error_str = errors.nil? ? '' : errors.join(', ')
152
- opts[:logger].error("Invalid event data received, #{error_str} #{parsed.inspect}")
82
+ return [parsed, errors]
153
83
  end
154
- nil
155
- rescue Oj::Error => e
156
- if opts[:logger]
157
- opts[:logger].error("Error deserialising event json: #{e}, raw json: #{raw.inspect}")
158
- end
159
- nil
84
+ [nil, errors]
85
+ rescue JSON::JSONError => e
86
+ errors << "Error deserialising event json: #{e}, raw json: #{raw.inspect}"
87
+ [nil, errors]
160
88
  end
161
89
 
162
90
  def self.validation_errors_for_hash(hash, opts = {})
@@ -185,67 +113,84 @@ module Flapjack
185
113
  # creates, or modifies, an event object and adds it to the events list in redis
186
114
  # 'entity' => entity,
187
115
  # 'check' => check,
116
+ # 'time' => timestamp,
117
+ # 'initial_failure_delay' => initial_failure_delay,
118
+ # 'repeat_failure_delay' => repeat_failure_delay
188
119
  # 'type' => 'service',
189
120
  # 'state' => state,
190
121
  # 'summary' => check_output,
191
122
  # 'details' => check_long_output,
192
- # 'perfdata' => perf_data,
193
- # 'time' => timestamp,
194
- # 'initial_failure_delay' => initial_failure_delay,
195
- # 'repeat_failure_delay' => repeat_failure_delay
196
- def self.add(evt, opts = {})
197
- raise "Redis connection not set" unless redis = opts[:redis]
123
+ # 'perfdata' => perf_data
124
+ def self.push(queue, event)
125
+ event['time'] = Time.now.to_i if event['time'].nil?
126
+
127
+ begin
128
+ event_json = Flapjack.dump_json(event)
129
+ rescue JSON::JSONError => e
130
+ Flapjack.logger.warn("Error serialising event json: #{e}, event: #{event.inspect}")
131
+ event_json = nil
132
+ end
198
133
 
199
- evt['time'] = Time.now.to_i if evt['time'].nil?
200
- redis.lpush('events', ::Flapjack.dump_json(evt))
134
+ if event_json
135
+ Flapjack.redis.multi do
136
+ Flapjack.redis.lpush(queue, event_json)
137
+ Flapjack.redis.lpush("#{queue}_actions", "+")
138
+ end
139
+ end
201
140
  end
202
141
 
203
142
  # Provide a count of the number of events on the queue to be processed.
204
- def self.pending_count(queue, opts = {})
205
- raise "Redis connection not set" unless redis = opts[:redis]
206
-
207
- redis.llen(queue)
208
- end
209
-
210
- def self.create_acknowledgement(entity_name, check, opts = {})
211
- data = { 'type' => 'action',
212
- 'state' => 'acknowledgement',
213
- 'entity' => entity_name,
214
- 'check' => check,
215
- 'summary' => opts[:summary],
216
- 'duration' => opts[:duration],
217
- 'acknowledgement_id' => opts[:acknowledgement_id]
218
- }
219
- add(data, :redis => opts[:redis])
143
+ def self.pending_count(queue)
144
+ Flapjack.redis.llen(queue)
145
+ end
146
+
147
+ def self.create_acknowledgements(queue, checks, opts = {})
148
+ raise "Check(s) must be provided" if checks.nil?
149
+ checks.each do |check|
150
+ self.push(queue, 'state' => 'acknowledgement',
151
+ 'check' => check.name,
152
+ 'summary' => opts[:summary],
153
+ 'duration' => opts[:duration],
154
+ 'acknowledgement_id' => opts[:acknowledgement_id])
155
+ end
220
156
  end
221
157
 
222
- def self.test_notifications(entity_name, check, opts = {})
223
- data = { 'type' => 'action',
224
- 'state' => 'test_notifications',
225
- 'entity' => entity_name,
226
- 'check' => check,
227
- 'summary' => opts[:summary],
228
- 'details' => opts[:details]
229
- }
230
- add(data, :redis => opts[:redis])
158
+ def self.test_notifications(queue, checks, opts = {})
159
+ raise "Check(s) must be provided" if checks.nil?
160
+ condition = opts[:condition] || 'critical'
161
+ unless Flapjack::Data::Condition.unhealthy.keys.include?(condition)
162
+ raise "Condition must be a problem"
163
+ end
164
+ checks.each do |check|
165
+ self.push(queue, 'state' => "test_notifications #{condition}",
166
+ 'check' => check.name,
167
+ 'summary' => opts[:summary],
168
+ 'details' => opts[:details])
169
+ end
231
170
  end
232
171
 
233
172
  def initialize(attrs = {})
234
- ['type', 'state', 'entity', 'check', 'time', 'summary', 'details',
235
- 'perfdata', 'acknowledgement_id', 'duration', 'initial_failure_delay',
236
- 'repeat_failure_delay'].each do |key|
173
+ @id = if attrs['entity'].nil?
174
+ attrs['check']
175
+ else
176
+ "#{attrs['entity']}:#{attrs['check']}"
177
+ end
178
+ [:state, :time, :initial_failure_delay, :repeat_failure_delay,
179
+ :summary, :details, :perfdata, :acknowledgement_id,
180
+ :duration].each do |key|
237
181
 
238
- instance_variable_set("@#{key}", Flapjack.sanitize(attrs[key]))
182
+ instance_variable_set("@#{key.to_s}", attrs[key.to_s])
239
183
  end
240
- # summary is optional. set it to nil if it only contains whitespace
241
- @summary = (@summary.is_a?(String) && ! @summary.strip.empty?) ? @summary.strip : nil
242
- # details is optional. set it to nil if it only contains whitespace
243
- @details = (@details.is_a?(String) && ! @details.strip.empty?) ? @details.strip : nil
244
- # perfdata is optional. set it to nil if it only contains whitespace
245
- @perfdata = (@perfdata.is_a?(String) && ! @perfdata.strip.empty?) ? @perfdata.strip : nil
246
- if attrs['tags']
247
- @tags = Set.new
248
- attrs['tags'].each {|tag| @tags.add(tag)}
184
+ # summary, details and perfdata are optional. set to nil if they only contain whitespace
185
+ ['@summary', '@details', '@perfdata'].each do |inst|
186
+ value = instance_variable_get(inst)
187
+ v = if value.is_a?(String)
188
+ vs = value.strip
189
+ vs.empty? ? nil : vs
190
+ else
191
+ nil
192
+ end
193
+ instance_variable_set(inst, v)
249
194
  end
250
195
  end
251
196
 
@@ -254,54 +199,21 @@ module Flapjack
254
199
  @state.downcase
255
200
  end
256
201
 
257
- def entity
258
- return unless @entity
259
- @entity.downcase
260
- end
261
-
262
- def duration
263
- return unless @duration
264
- @duration.to_i
265
- end
266
-
267
- def time
268
- return unless @time
269
- @time.to_i
270
- end
271
-
272
- def id
273
- (entity || '-') + ':' + (check || '-')
274
- end
275
-
276
- def type
277
- return unless @type
278
- @type.downcase
279
- end
280
-
281
- def service?
282
- type == 'service'
283
- end
284
-
285
- def acknowledgement?
286
- (type == 'action') && (state == 'acknowledgement')
287
- end
288
-
289
- def test_notifications?
290
- (type == 'action') && (state == 'test_notifications')
291
- end
292
-
293
- def ok?
294
- (state == 'ok') || (state == 'up')
202
+ [:time, :initial_failure_delay, :repeat_failure_delay, :duration].each do |num_prop|
203
+ define_method(num_prop) do
204
+ prop = instance_variable_get("@#{num_prop}")
205
+ return if prop.nil?
206
+ prop.to_i
207
+ end
295
208
  end
296
209
 
297
- def failure?
298
- ['critical', 'warning', 'unknown', 'down', 'unreachable'].include?(state)
210
+ def dump
211
+ return @dump unless @dump.nil?
212
+ @dump = "#{id}, #{state}"
213
+ @dump << ", #{summary}" unless summary.nil?
214
+ @dump << ", #{Time.at(time).to_s}" unless time.nil?
299
215
  end
300
-
301
- # # Not used anywhere
302
- # def unreachable?
303
- # state == 'unreachable'
304
- # end
305
216
  end
306
217
  end
307
218
  end
219
+
@@ -0,0 +1,59 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'active_support/concern'
4
+ require 'active_support/inflector'
5
+ require 'active_support/core_ext/hash/slice'
6
+
7
+ require 'sinatra/base'
8
+
9
+ require 'flapjack/gateways/jsonapi/data/join_descriptor'
10
+ require 'flapjack/gateways/jsonapi/data/method_descriptor'
11
+
12
+ module Flapjack
13
+ module Data
14
+ module Extensions
15
+ module Associations
16
+
17
+ extend ActiveSupport::Concern
18
+
19
+ module ClassMethods
20
+
21
+ def jsonapi_lock_method(http_method, locks = nil, &block)
22
+ locks ||= []
23
+
24
+ if :delete.eql?(http_method)
25
+ # all associations, not just the ones exposed via JSONAPI
26
+ self.send(:with_association_data) do |assoc_data|
27
+ assoc_data.each_pair do |name, data|
28
+ locks |= [data.data_klass] + data.related_klasses
29
+ end
30
+ end
31
+
32
+ locks |= jsonapi_associations.values.select {|a|
33
+ !a.type.nil?
34
+ }.map(&:lock_klasses).reduce([], :|)
35
+ end
36
+
37
+ if locks.empty?
38
+ self.lock(&block)
39
+ else
40
+ locks.sort_by!(&:name)
41
+ self.lock(*locks, &block)
42
+ end
43
+ end
44
+
45
+ def populate_association_data(jsonapi_assoc)
46
+ # SMELL mucking about with a zermelo protected method...
47
+ self.send(:with_association_data) do |assoc_data|
48
+ assoc_data.each_pair do |name, data|
49
+ ja = jsonapi_assoc[name.to_sym]
50
+ next if ja.nil?
51
+ ja.association_data = data
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'securerandom'
4
+
5
+ require 'active_support/concern'
6
+
7
+ require 'swagger/blocks'
8
+
9
+ module Flapjack
10
+ module Data
11
+ module Extensions
12
+ module ShortName
13
+ extend ActiveSupport::Concern
14
+
15
+ module ClassMethods
16
+
17
+ def short_model_name
18
+ ActiveModel::Name.new(self, Flapjack::Data, self.name.demodulize)
19
+ end
20
+
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,428 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'swagger/blocks'
4
+
5
+ require 'zermelo/records/redis'
6
+
7
+ require 'flapjack/data/alert'
8
+ require 'flapjack/data/check'
9
+ require 'flapjack/data/contact'
10
+ require 'flapjack/data/rule'
11
+ require 'flapjack/data/scheduled_maintenance'
12
+ require 'flapjack/data/unscheduled_maintenance'
13
+
14
+ require 'flapjack/data/extensions/associations'
15
+ require 'flapjack/data/extensions/short_name'
16
+ require 'flapjack/data/validators/id_validator'
17
+
18
+ require 'flapjack/gateways/jsonapi/data/join_descriptor'
19
+ require 'flapjack/gateways/jsonapi/data/method_descriptor'
20
+
21
+ module Flapjack
22
+
23
+ module Data
24
+
25
+ class Medium
26
+
27
+ include Zermelo::Records::RedisSet
28
+ include ActiveModel::Serializers::JSON
29
+ self.include_root_in_json = false
30
+ include Swagger::Blocks
31
+
32
+ include Flapjack::Data::Extensions::Associations
33
+ include Flapjack::Data::Extensions::ShortName
34
+
35
+ TRANSPORTS = [
36
+ 'email',
37
+ 'jabber',
38
+ 'pagerduty',
39
+ 'sms',
40
+ 'slack',
41
+ 'sms_twilio',
42
+ 'sms_nexmo',
43
+ 'sms_aspsms',
44
+ 'sns'
45
+ ]
46
+
47
+ define_attributes :transport => :string,
48
+ :address => :string,
49
+ :interval => :integer,
50
+ :rollup_threshold => :integer,
51
+ :pagerduty_subdomain => :string,
52
+ :pagerduty_token => :string,
53
+ :pagerduty_ack_duration => :integer,
54
+ :last_rollup_type => :string
55
+
56
+ belongs_to :contact, :class_name => 'Flapjack::Data::Contact',
57
+ :inverse_of => :media
58
+
59
+ has_and_belongs_to_many :rules, :class_name => 'Flapjack::Data::Rule',
60
+ :inverse_of => :media
61
+
62
+ # this can be called from the API (with no args) or from notifier.rb
63
+ # (which will pass an effective time)
64
+ def alerting_checks(opts = {})
65
+ time = opts[:time] || Time.now
66
+ init_scope = Flapjack::Data::Check.intersect(:enabled => true, :alertable => true)
67
+ ret = checks(:initial_scope => init_scope,
68
+ :time => Time.now)
69
+
70
+ return Flapjack::Data::Check.empty if ret.empty?
71
+
72
+ start_range = Zermelo::Filters::IndexRange.new(nil, time, :by_score => true)
73
+ end_range = Zermelo::Filters::IndexRange.new(time, nil, :by_score => true)
74
+
75
+ sched_maint_check_ids = Flapjack::Data::ScheduledMaintenance.
76
+ intersect(:start_time => start_range, :end_time => end_range).
77
+ associated_ids_for(:check).values
78
+
79
+ ret = ret.diff(:id => sched_maint_check_ids) unless sched_maint_check_ids.empty?
80
+
81
+ unsched_maint_check_ids = Flapjack::Data::UnscheduledMaintenance.
82
+ intersect(:start_time => start_range, :end_time => end_range).
83
+ associated_ids_for(:check).values
84
+
85
+ ret = ret.diff(:id => unsched_maint_check_ids) unless unsched_maint_check_ids.empty?
86
+ ret
87
+ end
88
+
89
+ def checks(opts = {})
90
+ time_zone = self.contact.time_zone
91
+ time = opts[:time] || Time.now
92
+ init_scope = opts[:initial_scope] || Flapjack::Data::Check.intersect(:enabled => true)
93
+
94
+ # TODO maybe fold time validation into 'matching_checks'
95
+ global_rejector_ids = self.rules.intersect(:enabled => true, :blackhole => true,
96
+ :strategy => 'global').select {|rejector|
97
+
98
+ rejector.is_occurring_at?(time, time_zone)
99
+ }.map(&:id)
100
+
101
+ unless global_rejector_ids.empty?
102
+ # global blackhole
103
+ return Flapjack::Data::Check.empty
104
+ end
105
+
106
+ rejector_ids = self.rules.intersect(:enabled => true, :blackhole => true,
107
+ :strategy => ['all_tags', 'any_tag', 'no_tag']).select {|rejector|
108
+
109
+ rejector.is_occurring_at?(time, time_zone)
110
+ }.map(&:id)
111
+
112
+ acceptors = self.rules.intersect(:enabled => true, :blackhole => false).select {|acceptor|
113
+ acceptor.is_occurring_at?(time, time_zone)
114
+ }
115
+
116
+ # no positives
117
+ return Flapjack::Data::Check.empty if acceptors.empty?
118
+
119
+ ret = init_scope
120
+
121
+ if acceptors.none? {|a| 'global'.eql?(a.strategy) }
122
+ # if no global acceptor, scope by tags for acceptors
123
+ acceptor_checks = Flapjack::Data::Rule.matching_checks(acceptors.map(&:id))
124
+ ret = ret.intersect(:id => acceptor_checks)
125
+ end
126
+
127
+ # then exclude by checks with tags matching rejector, if any
128
+ rejector_checks = Flapjack::Data::Rule.matching_checks(rejector_ids)
129
+ unless rejector_checks.empty?
130
+ ret = ret.diff(:id => rejector_checks)
131
+ end
132
+
133
+ ret
134
+ end
135
+
136
+ has_many :alerts, :class_name => 'Flapjack::Data::Alert', :inverse_of => :medium
137
+
138
+ belongs_to :last_state, :class_name => 'Flapjack::Data::State',
139
+ :inverse_of => :latest_media, :after_clear => :destroy_state
140
+
141
+ def self.destroy_state(medium_id, st_id)
142
+ # won't be deleted if still referenced elsewhere -- see the State
143
+ # before_destroy callback
144
+ Flapjack::Data::State.intersect(:id => st_id).destroy_all
145
+ end
146
+
147
+ index_by :transport
148
+
149
+ validates :transport, :presence => true,
150
+ :inclusion => {:in => Flapjack::Data::Medium::TRANSPORTS }
151
+
152
+ validates :address, :presence => true
153
+
154
+ validates :interval, :presence => true,
155
+ :numericality => {:greater_than_or_equal_to => 0, :only_integer => true},
156
+ :unless => proc {|m| 'pagerduty'.eql?(m.transport) }
157
+
158
+ validates :rollup_threshold, :allow_nil => true,
159
+ :numericality => {:greater_than => 0, :only_integer => true},
160
+ :unless => proc {|m| 'pagerduty'.eql?(m.transport) }
161
+
162
+ validates_each :interval, :rollup_threshold,
163
+ :if => proc {|m| 'pagerduty'.eql?(m.transport) } do |record, att, value|
164
+
165
+ record.errors.add(att, 'must be nil') unless value.nil?
166
+ end
167
+
168
+ validates :pagerduty_subdomain, :presence => true,
169
+ :if => proc {|m| 'pagerduty'.eql?(m.transport) }
170
+
171
+ validates :pagerduty_token, :presence => true,
172
+ :if => proc {|m| 'pagerduty'.eql?(m.transport) }
173
+
174
+ validates :pagerduty_ack_duration, :allow_nil => true,
175
+ :numericality => {:greater_than => 0, :only_integer => true},
176
+ :if => proc {|m| 'pagerduty'.eql?(m.transport) }
177
+
178
+ validates_each :pagerduty_subdomain, :pagerduty_token,
179
+ :pagerduty_ack_duration,
180
+ :unless => proc {|m| 'pagerduty'.eql?(m.transport) } do |record, att, value|
181
+ record.errors.add(att, 'must be nil') unless value.nil?
182
+ end
183
+
184
+ validates_with Flapjack::Data::Validators::IdValidator
185
+
186
+ swagger_schema :Medium do
187
+ key :required, [:id, :type, :transport]
188
+
189
+ property :id do
190
+ key :type, :string
191
+ key :format, :uuid
192
+ end
193
+ property :type do
194
+ key :type, :string
195
+ key :enum, [Flapjack::Data::Medium.short_model_name.singular]
196
+ end
197
+ property :transport do
198
+ key :type, :string
199
+ key :enum, Flapjack::Data::Medium::TRANSPORTS.map(&:to_sym)
200
+ end
201
+ property :address do
202
+ key :type, :string
203
+ end
204
+ property :interval do
205
+ key :type, :integer
206
+ key :minimum, 0
207
+ end
208
+ property :rollup_threshold do
209
+ key :type, :integer
210
+ key :minimum, 1
211
+ end
212
+ property :pagerduty_subdomain do
213
+ key :type, :string
214
+ end
215
+ property :pagerduty_token do
216
+ key :type, :string
217
+ end
218
+ property :pagerduty_ack_duration do
219
+ key :type, :integer
220
+ key :minimum, 1
221
+ end
222
+ property :relationships do
223
+ key :"$ref", :MediumLinks
224
+ end
225
+ end
226
+
227
+ swagger_schema :MediumLinks do
228
+ key :required, [:contact, :rules]
229
+ property :contact do
230
+ key :"$ref", :ContactLinkage
231
+ end
232
+ property :rules do
233
+ key :"$ref", :RulesLinkage
234
+ end
235
+ end
236
+
237
+ swagger_schema :MediumCreate do
238
+ key :required, [:type, :address, :transport]
239
+ property :id do
240
+ key :type, :string
241
+ key :format, :uuid
242
+ end
243
+ property :type do
244
+ key :type, :string
245
+ key :enum, [Flapjack::Data::Medium.short_model_name.singular]
246
+ end
247
+ property :transport do
248
+ key :type, :string
249
+ key :enum, Flapjack::Data::Medium::TRANSPORTS.map(&:to_sym)
250
+ end
251
+ property :address do
252
+ key :type, :string
253
+ end
254
+ property :interval do
255
+ key :type, :integer
256
+ key :minimum, 0
257
+ end
258
+ property :rollup_threshold do
259
+ key :type, :integer
260
+ key :minimum, 1
261
+ end
262
+ property :pagerduty_subdomain do
263
+ key :type, :string
264
+ end
265
+ property :pagerduty_token do
266
+ key :type, :string
267
+ end
268
+ property :pagerduty_ack_duration do
269
+ key :type, :integer
270
+ key :minimum, 1
271
+ end
272
+ property :relationships do
273
+ key :"$ref", :MediumCreateLinks
274
+ end
275
+ end
276
+
277
+ swagger_schema :MediumCreateLinks do
278
+ key :required, [:contact]
279
+ property :contact do
280
+ key :"$ref", :data_ContactReference
281
+ end
282
+ property :rules do
283
+ key :"$ref", :data_RulesReference
284
+ end
285
+ end
286
+
287
+ swagger_schema :MediumUpdate do
288
+ key :required, [:id, :type]
289
+ property :id do
290
+ key :type, :string
291
+ key :format, :uuid
292
+ end
293
+ property :type do
294
+ key :type, :string
295
+ key :enum, [Flapjack::Data::Medium.short_model_name.singular]
296
+ end
297
+ property :transport do
298
+ key :type, :string
299
+ key :enum, Flapjack::Data::Medium::TRANSPORTS.map(&:to_sym)
300
+ end
301
+ property :address do
302
+ key :type, :string
303
+ end
304
+ property :interval do
305
+ key :type, :integer
306
+ key :minimum, 0
307
+ end
308
+ property :rollup_threshold do
309
+ key :type, :integer
310
+ key :minimum, 1
311
+ end
312
+ property :pagerduty_subdomain do
313
+ key :type, :string
314
+ end
315
+ property :pagerduty_token do
316
+ key :type, :string
317
+ end
318
+ property :pagerduty_ack_duration do
319
+ key :type, :integer
320
+ key :minimum, 1
321
+ end
322
+ property :relationships do
323
+ key :"$ref", :MediumUpdateLinks
324
+ end
325
+ end
326
+
327
+ swagger_schema :MediumUpdateLinks do
328
+ property :rules do
329
+ key :"$ref", :data_RulesReference
330
+ end
331
+ end
332
+
333
+ def self.swagger_included_classes
334
+ # hack -- hardcoding for now
335
+ [
336
+ Flapjack::Data::Check,
337
+ Flapjack::Data::Contact,
338
+ Flapjack::Data::Medium,
339
+ Flapjack::Data::Rule,
340
+ Flapjack::Data::ScheduledMaintenance,
341
+ Flapjack::Data::State,
342
+ Flapjack::Data::Tag,
343
+ Flapjack::Data::UnscheduledMaintenance
344
+ ]
345
+ end
346
+
347
+ def self.jsonapi_methods
348
+ @jsonapi_methods ||= {
349
+ :post => Flapjack::Gateways::JSONAPI::Data::MethodDescriptor.new(
350
+ :attributes => [:transport, :address, :interval, :rollup_threshold,
351
+ :pagerduty_subdomain, :pagerduty_token,
352
+ :pagerduty_ack_duration],
353
+ :descriptions => {
354
+ :singular => "Create a media record.",
355
+ :multiple => "Create media records."
356
+ }
357
+ ),
358
+ :get => Flapjack::Gateways::JSONAPI::Data::MethodDescriptor.new(
359
+ :attributes => [:transport, :address, :interval, :rollup_threshold,
360
+ :pagerduty_subdomain, :pagerduty_token,
361
+ :pagerduty_ack_duration],
362
+ :descriptions => {
363
+ :singular => "Returns data for a media record.",
364
+ :multiple => "Returns data for media records."
365
+ }
366
+ ),
367
+ :patch => Flapjack::Gateways::JSONAPI::Data::MethodDescriptor.new(
368
+ :attributes => [:transport, :address, :interval, :rollup_threshold,
369
+ :pagerduty_subdomain, :pagerduty_token,
370
+ :pagerduty_ack_duration],
371
+ :descriptions => {
372
+ :singular => "Update a media record.",
373
+ :multiple => "Update media records."
374
+ }
375
+ ),
376
+ :delete => Flapjack::Gateways::JSONAPI::Data::MethodDescriptor.new(
377
+ :descriptions => {
378
+ :singular => "Delete a media record.",
379
+ :multiple => "Delete media records."
380
+ }
381
+ )
382
+ }
383
+ end
384
+
385
+ def self.jsonapi_associations
386
+ unless instance_variable_defined?('@jsonapi_associations')
387
+ @jsonapi_associations = {
388
+ :alerting_checks => Flapjack::Gateways::JSONAPI::Data::JoinDescriptor.new(
389
+ :get => true,
390
+ :number => :multiple, :link => true, :includable => true,
391
+ :type => 'check',
392
+ :klass => Flapjack::Data::Check,
393
+ :callback_classes => [
394
+ Flapjack::Data::Contact,
395
+ Flapjack::Data::Rule,
396
+ Flapjack::Data::ScheduledMaintenance
397
+ ],
398
+ :descriptions => {
399
+ :get => "Returns all checks that have alerted through a medium (that are still failing."
400
+ }
401
+ ),
402
+ :contact => Flapjack::Gateways::JSONAPI::Data::JoinDescriptor.new(
403
+ :post => true, :get => true,
404
+ :number => :singular, :link => true, :includable => true,
405
+ :descriptions => {
406
+ :post => "Set a contact for a medium during medium creation (required).",
407
+ :get => "Get the contact a medium belongs to."
408
+ }
409
+ ),
410
+ :rules => Flapjack::Gateways::JSONAPI::Data::JoinDescriptor.new(
411
+ :post => true, :get => true, :patch => true, :delete => true,
412
+ :number => :multiple, :link => true, :includable => true,
413
+ :descriptions => {
414
+ :post => "Associate this medium with rules on medium creation.",
415
+ :get => "Get the rules this medium is associated with.",
416
+ :patch => "Update the rules this medium is associated with.",
417
+ :delete => "Delete associations between this medium and rules."
418
+ }
419
+
420
+ )
421
+ }
422
+ populate_association_data(@jsonapi_associations)
423
+ end
424
+ @jsonapi_associations
425
+ end
426
+ end
427
+ end
428
+ end