kuroko2 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (338) hide show
  1. checksums.yaml +7 -0
  2. data/MIT-LICENSE +20 -0
  3. data/README.md +15 -0
  4. data/Rakefile +26 -0
  5. data/app/assets/images/kuroko2/avatar.png +0 -0
  6. data/app/assets/images/kuroko2/kuroko-logo-horizontal.png +0 -0
  7. data/app/assets/javascripts/kuroko2/application.js +28 -0
  8. data/app/assets/javascripts/kuroko2/bootstrap.js +2363 -0
  9. data/app/assets/javascripts/kuroko2/definition_linker.js +20 -0
  10. data/app/assets/javascripts/kuroko2/instance_linker.js +10 -0
  11. data/app/assets/javascripts/kuroko2/job_definition_stats.js +67 -0
  12. data/app/assets/javascripts/kuroko2/job_definitions.js +79 -0
  13. data/app/assets/javascripts/kuroko2/job_instances.js +88 -0
  14. data/app/assets/javascripts/kuroko2/job_timelines.js.coffee +24 -0
  15. data/app/assets/javascripts/kuroko2/narrow_job_definitions.js +30 -0
  16. data/app/assets/stylesheets/kuroko2/admin-lte.css +3402 -0
  17. data/app/assets/stylesheets/kuroko2/application.scss +86 -0
  18. data/app/assets/stylesheets/kuroko2/bootstrap.css +6799 -0
  19. data/app/assets/stylesheets/kuroko2/fonts.scss +1 -0
  20. data/app/assets/stylesheets/kuroko2/job_definitions.scss +19 -0
  21. data/app/assets/stylesheets/kuroko2/users.scss +7 -0
  22. data/app/controllers/kuroko2/api/application_controller.rb +49 -0
  23. data/app/controllers/kuroko2/api/job_instances_controller.rb +46 -0
  24. data/app/controllers/kuroko2/api/stats_controller.rb +28 -0
  25. data/app/controllers/kuroko2/application_controller.rb +43 -0
  26. data/app/controllers/kuroko2/dashboard_controller.rb +27 -0
  27. data/app/controllers/kuroko2/execution_logs_controller.rb +19 -0
  28. data/app/controllers/kuroko2/executions_controller.rb +28 -0
  29. data/app/controllers/kuroko2/job_definition_stats_controller.rb +54 -0
  30. data/app/controllers/kuroko2/job_definitions_controller.rb +100 -0
  31. data/app/controllers/kuroko2/job_instances_controller.rb +87 -0
  32. data/app/controllers/kuroko2/job_schedules_controller.rb +39 -0
  33. data/app/controllers/kuroko2/job_suspend_schedules_controller.rb +38 -0
  34. data/app/controllers/kuroko2/job_timelines_controller.rb +56 -0
  35. data/app/controllers/kuroko2/logs_controller.rb +15 -0
  36. data/app/controllers/kuroko2/sessions_controller.rb +32 -0
  37. data/app/controllers/kuroko2/stars_controller.rb +30 -0
  38. data/app/controllers/kuroko2/tokens_controller.rb +47 -0
  39. data/app/controllers/kuroko2/users_controller.rb +62 -0
  40. data/app/controllers/kuroko2/workers_controller.rb +5 -0
  41. data/app/errors/http/bad_request.rb +4 -0
  42. data/app/errors/http/forbidden.rb +4 -0
  43. data/app/errors/http/unauthorized.rb +4 -0
  44. data/app/helpers/kuroko2/application_helper.rb +8 -0
  45. data/app/helpers/kuroko2/dashboard_helper.rb +4 -0
  46. data/app/helpers/kuroko2/executions_helper.rb +4 -0
  47. data/app/helpers/kuroko2/job_definitions_helper.rb +38 -0
  48. data/app/helpers/kuroko2/job_instances_helper.rb +71 -0
  49. data/app/helpers/kuroko2/job_schedules_helper.rb +4 -0
  50. data/app/helpers/kuroko2/logs_helper.rb +4 -0
  51. data/app/helpers/kuroko2/sessions_helper.rb +4 -0
  52. data/app/helpers/kuroko2/stars_helper.rb +4 -0
  53. data/app/helpers/kuroko2/tokens_helper.rb +4 -0
  54. data/app/helpers/kuroko2/users_helper.rb +4 -0
  55. data/app/helpers/kuroko2/workers_helper.rb +4 -0
  56. data/app/jobs/kuroko2/application_job.rb +4 -0
  57. data/app/mailers/kuroko2/application_mailer.rb +6 -0
  58. data/app/mailers/kuroko2/notifications.rb +63 -0
  59. data/app/models/concerns/kuroko2/table_name_customizable.rb +16 -0
  60. data/app/models/kuroko2/admin_assignment.rb +6 -0
  61. data/app/models/kuroko2/api/application_resource.rb +10 -0
  62. data/app/models/kuroko2/api/job_instance_resource.rb +7 -0
  63. data/app/models/kuroko2/application_record.rb +5 -0
  64. data/app/models/kuroko2/execution.rb +55 -0
  65. data/app/models/kuroko2/job_definition.rb +147 -0
  66. data/app/models/kuroko2/job_definition_tag.rb +6 -0
  67. data/app/models/kuroko2/job_instance.rb +118 -0
  68. data/app/models/kuroko2/job_schedule.rb +93 -0
  69. data/app/models/kuroko2/job_suspend_schedule.rb +35 -0
  70. data/app/models/kuroko2/log.rb +3 -0
  71. data/app/models/kuroko2/memory_consumption_log.rb +49 -0
  72. data/app/models/kuroko2/memory_expectancy.rb +21 -0
  73. data/app/models/kuroko2/process_signal.rb +14 -0
  74. data/app/models/kuroko2/star.rb +6 -0
  75. data/app/models/kuroko2/tag.rb +8 -0
  76. data/app/models/kuroko2/tick.rb +12 -0
  77. data/app/models/kuroko2/token.rb +101 -0
  78. data/app/models/kuroko2/user.rb +48 -0
  79. data/app/models/kuroko2/worker.rb +12 -0
  80. data/app/views/kaminari/history/_paginator.html.slim +15 -0
  81. data/app/views/kaminari/list/_paginator.html.slim +17 -0
  82. data/app/views/kuroko2/dashboard/_taglist.html.slim +13 -0
  83. data/app/views/kuroko2/dashboard/index.html.slim +49 -0
  84. data/app/views/kuroko2/execution_logs/index.json.jbuilder +16 -0
  85. data/app/views/kuroko2/executions/index.html.slim +35 -0
  86. data/app/views/kuroko2/job_definition_stats/execution_time.json.jbuilder +13 -0
  87. data/app/views/kuroko2/job_definition_stats/index.html.slim +48 -0
  88. data/app/views/kuroko2/job_definition_stats/memory.json.jbuilder +10 -0
  89. data/app/views/kuroko2/job_definitions/_alert.html.slim +7 -0
  90. data/app/views/kuroko2/job_definitions/_form.html.slim +93 -0
  91. data/app/views/kuroko2/job_definitions/_list.html.slim +26 -0
  92. data/app/views/kuroko2/job_definitions/_search_results.html.slim +51 -0
  93. data/app/views/kuroko2/job_definitions/_taglist.html.slim +13 -0
  94. data/app/views/kuroko2/job_definitions/edit.html.slim +15 -0
  95. data/app/views/kuroko2/job_definitions/index.html.slim +11 -0
  96. data/app/views/kuroko2/job_definitions/new.html.slim +12 -0
  97. data/app/views/kuroko2/job_definitions/show.html.slim +90 -0
  98. data/app/views/kuroko2/job_instances/_instance.html.slim +42 -0
  99. data/app/views/kuroko2/job_instances/index.html.slim +58 -0
  100. data/app/views/kuroko2/job_instances/show.html.slim +19 -0
  101. data/app/views/kuroko2/job_instances/working.html.slim +37 -0
  102. data/app/views/kuroko2/job_schedules/index.html.slim +32 -0
  103. data/app/views/kuroko2/job_suspend_schedules/index.html.slim +27 -0
  104. data/app/views/kuroko2/job_timelines/dataset.json.jbuilder +11 -0
  105. data/app/views/kuroko2/job_timelines/index.html.slim +31 -0
  106. data/app/views/kuroko2/kaminari/history/_paginator.html.slim +15 -0
  107. data/app/views/kuroko2/kaminari/list/_paginator.html.slim +17 -0
  108. data/app/views/kuroko2/layouts/application.html.slim +68 -0
  109. data/app/views/kuroko2/logs/index.html.slim +33 -0
  110. data/app/views/kuroko2/notifications/executor_not_assigned.text.erb +22 -0
  111. data/app/views/kuroko2/notifications/job_failure.html.slim +21 -0
  112. data/app/views/kuroko2/notifications/job_failure.text.erb +18 -0
  113. data/app/views/kuroko2/notifications/notify_long_elapsed_time.text.erb +9 -0
  114. data/app/views/kuroko2/notifications/process_absence.text.erb +22 -0
  115. data/app/views/kuroko2/notifications/remind_failure.html.slim +21 -0
  116. data/app/views/kuroko2/notifications/remind_failure.text.erb +10 -0
  117. data/app/views/kuroko2/sessions/new.html.slim +20 -0
  118. data/app/views/kuroko2/tokens/index.html.slim +42 -0
  119. data/app/views/kuroko2/users/index.html.slim +55 -0
  120. data/app/views/kuroko2/users/show.html.slim +76 -0
  121. data/app/views/kuroko2/workers/index.html.slim +40 -0
  122. data/app/views/layouts/kuroko2/application.html.slim +72 -0
  123. data/app/views/layouts/mailer.html.erb +13 -0
  124. data/app/views/layouts/mailer.text.erb +1 -0
  125. data/bin/cleanup_old_instances.rb +9 -0
  126. data/bin/remind_failure.rb +5 -0
  127. data/config/initializers/000_kuroko2.rb +16 -0
  128. data/config/initializers/assets.rb +9 -0
  129. data/config/initializers/garage.rb +2 -0
  130. data/config/initializers/kaminari_config.rb +3 -0
  131. data/config/initializers/omniauth.rb +5 -0
  132. data/config/locales/en.yml +28 -0
  133. data/config/routes.rb +54 -0
  134. data/db/migrate/001_create_job_definitions.rb +22 -0
  135. data/db/migrate/002_create_job_instances.rb +17 -0
  136. data/db/migrate/003_create_job_schedules.rb +14 -0
  137. data/db/migrate/004_create_ticks.rb +7 -0
  138. data/db/migrate/005_create_logs.rb +13 -0
  139. data/db/migrate/006_create_tokens.rb +21 -0
  140. data/db/migrate/007_create_executions.rb +26 -0
  141. data/db/migrate/008_create_process_signals.rb +15 -0
  142. data/db/migrate/009_create_users.rb +20 -0
  143. data/db/migrate/010_create_admin_assignments.rb +12 -0
  144. data/db/migrate/011_create_stars.rb +12 -0
  145. data/db/migrate/012_create_workers.rb +15 -0
  146. data/db/migrate/018_create_job_definition_tags.rb +13 -0
  147. data/db/migrate/019_create_tags.rb +11 -0
  148. data/db/migrate/021_create_memory_expectancies.rb +17 -0
  149. data/db/migrate/025_create_job_suspend_schedules.rb +12 -0
  150. data/lib/kuroko2/command/executor.rb +62 -0
  151. data/lib/kuroko2/command/kill.rb +24 -0
  152. data/lib/kuroko2/command/monitor.rb +109 -0
  153. data/lib/kuroko2/command/shell.rb +163 -0
  154. data/lib/kuroko2/configuration.rb +19 -0
  155. data/lib/kuroko2/engine.rb +59 -0
  156. data/lib/kuroko2/execution_logger/cloud_watch_logs.rb +92 -0
  157. data/lib/kuroko2/execution_logger/void.rb +13 -0
  158. data/lib/kuroko2/execution_logger.rb +20 -0
  159. data/lib/kuroko2/memory_sampler.rb +50 -0
  160. data/lib/kuroko2/return_to_validator.rb +14 -0
  161. data/lib/kuroko2/servers/base.rb +30 -0
  162. data/lib/kuroko2/servers/command_executor.rb +27 -0
  163. data/lib/kuroko2/servers/job_scheduler.rb +25 -0
  164. data/lib/kuroko2/servers/workflow_processor.rb +25 -0
  165. data/lib/kuroko2/util/logger.rb +19 -0
  166. data/lib/kuroko2/util/rails_logger_formatter.rb +9 -0
  167. data/lib/kuroko2/version.rb +3 -0
  168. data/lib/kuroko2/workflow/assertion_error.rb +6 -0
  169. data/lib/kuroko2/workflow/engine.rb +141 -0
  170. data/lib/kuroko2/workflow/engine_error.rb +6 -0
  171. data/lib/kuroko2/workflow/node.rb +124 -0
  172. data/lib/kuroko2/workflow/notifier/concerns/chat_message_builder.rb +39 -0
  173. data/lib/kuroko2/workflow/notifier/hipchat.rb +88 -0
  174. data/lib/kuroko2/workflow/notifier/mail.rb +44 -0
  175. data/lib/kuroko2/workflow/notifier/slack.rb +121 -0
  176. data/lib/kuroko2/workflow/notifier.rb +31 -0
  177. data/lib/kuroko2/workflow/processor.rb +40 -0
  178. data/lib/kuroko2/workflow/scheduler.rb +42 -0
  179. data/lib/kuroko2/workflow/script_parser.rb +66 -0
  180. data/lib/kuroko2/workflow/shell_scanner.rb +34 -0
  181. data/lib/kuroko2/workflow/syntax_error.rb +6 -0
  182. data/lib/kuroko2/workflow/task/auto_skip_error.rb +20 -0
  183. data/lib/kuroko2/workflow/task/base.rb +32 -0
  184. data/lib/kuroko2/workflow/task/env.rb +45 -0
  185. data/lib/kuroko2/workflow/task/execute.rb +128 -0
  186. data/lib/kuroko2/workflow/task/expected_time.rb +9 -0
  187. data/lib/kuroko2/workflow/task/fork.rb +45 -0
  188. data/lib/kuroko2/workflow/task/kuroko_runner.rb +24 -0
  189. data/lib/kuroko2/workflow/task/noop.rb +13 -0
  190. data/lib/kuroko2/workflow/task/queue.rb +27 -0
  191. data/lib/kuroko2/workflow/task/rails_env.rb +24 -0
  192. data/lib/kuroko2/workflow/task/sequence.rb +13 -0
  193. data/lib/kuroko2/workflow/task/sleep.rb +29 -0
  194. data/lib/kuroko2/workflow/task/sub_process.rb +53 -0
  195. data/lib/kuroko2/workflow/task/time_base.rb +44 -0
  196. data/lib/kuroko2/workflow/task/timeout.rb +9 -0
  197. data/lib/kuroko2/workflow/task/wait.rb +143 -0
  198. data/lib/kuroko2.rb +26 -0
  199. data/lib/tasks/kuroko2_tasks.rake +4 -0
  200. data/spec/command/kill_spec.rb +20 -0
  201. data/spec/command/monitor_spec.rb +68 -0
  202. data/spec/command/shell_spec.rb +87 -0
  203. data/spec/controllers/dashboard_controller_spec.rb +5 -0
  204. data/spec/controllers/executions_controller_spec.rb +23 -0
  205. data/spec/controllers/job_definition_stats_controller_spec.rb +95 -0
  206. data/spec/controllers/job_definitions_controller_spec.rb +89 -0
  207. data/spec/controllers/job_instances_controller_spec.rb +62 -0
  208. data/spec/controllers/job_schedules_controller_spec.rb +39 -0
  209. data/spec/controllers/job_suspend_schedules_controller_spec.rb +39 -0
  210. data/spec/controllers/job_timelines_controller_spec.rb +114 -0
  211. data/spec/controllers/logs_controller_spec.rb +5 -0
  212. data/spec/controllers/sessions_controller_spec.rb +58 -0
  213. data/spec/controllers/stars_controller_spec.rb +28 -0
  214. data/spec/controllers/tokens_controller_spec.rb +5 -0
  215. data/spec/controllers/users_controller_spec.rb +51 -0
  216. data/spec/controllers/workers_controller_spec.rb +5 -0
  217. data/spec/dummy/Rakefile +6 -0
  218. data/spec/dummy/app/assets/config/manifest.js +5 -0
  219. data/spec/dummy/app/assets/javascripts/application.js +13 -0
  220. data/spec/dummy/app/assets/javascripts/cable.js +13 -0
  221. data/spec/dummy/app/assets/stylesheets/application.css +15 -0
  222. data/spec/dummy/app/channels/application_cable/channel.rb +4 -0
  223. data/spec/dummy/app/channels/application_cable/connection.rb +4 -0
  224. data/spec/dummy/app/controllers/application_controller.rb +3 -0
  225. data/spec/dummy/app/helpers/application_helper.rb +2 -0
  226. data/spec/dummy/app/jobs/application_job.rb +2 -0
  227. data/spec/dummy/app/mailers/application_mailer.rb +4 -0
  228. data/spec/dummy/app/models/application_record.rb +3 -0
  229. data/spec/dummy/app/views/layouts/application.html.erb +14 -0
  230. data/spec/dummy/app/views/layouts/mailer.html.erb +13 -0
  231. data/spec/dummy/app/views/layouts/mailer.text.erb +1 -0
  232. data/spec/dummy/bin/bundle +3 -0
  233. data/spec/dummy/bin/rails +4 -0
  234. data/spec/dummy/bin/rake +4 -0
  235. data/spec/dummy/bin/setup +34 -0
  236. data/spec/dummy/bin/update +29 -0
  237. data/spec/dummy/config/application.rb +25 -0
  238. data/spec/dummy/config/boot.rb +3 -0
  239. data/spec/dummy/config/cable.yml +9 -0
  240. data/spec/dummy/config/database.yml +29 -0
  241. data/spec/dummy/config/environment.rb +5 -0
  242. data/spec/dummy/config/environments/development.rb +54 -0
  243. data/spec/dummy/config/environments/production.rb +86 -0
  244. data/spec/dummy/config/environments/test.rb +42 -0
  245. data/spec/dummy/config/initializers/application_controller_renderer.rb +6 -0
  246. data/spec/dummy/config/initializers/assets.rb +11 -0
  247. data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
  248. data/spec/dummy/config/initializers/cookies_serializer.rb +5 -0
  249. data/spec/dummy/config/initializers/filter_parameter_logging.rb +4 -0
  250. data/spec/dummy/config/initializers/inflections.rb +16 -0
  251. data/spec/dummy/config/initializers/mime_types.rb +4 -0
  252. data/spec/dummy/config/initializers/new_framework_defaults.rb +23 -0
  253. data/spec/dummy/config/initializers/session_store.rb +3 -0
  254. data/spec/dummy/config/initializers/wrap_parameters.rb +14 -0
  255. data/spec/dummy/config/kuroko2.yml +35 -0
  256. data/spec/dummy/config/locales/en.yml +23 -0
  257. data/spec/dummy/config/puma.rb +47 -0
  258. data/spec/dummy/config/routes.rb +3 -0
  259. data/spec/dummy/config/secrets.yml +22 -0
  260. data/spec/dummy/config/spring.rb +6 -0
  261. data/spec/dummy/config.ru +5 -0
  262. data/spec/dummy/db/schema.rb +217 -0
  263. data/spec/dummy/lib/dummy_extention.rb +14 -0
  264. data/spec/dummy/lib/kuroko2/workflow/task/custom_task1.rb +13 -0
  265. data/spec/dummy/public/404.html +67 -0
  266. data/spec/dummy/public/422.html +67 -0
  267. data/spec/dummy/public/500.html +66 -0
  268. data/spec/dummy/public/apple-touch-icon-precomposed.png +0 -0
  269. data/spec/dummy/public/apple-touch-icon.png +0 -0
  270. data/spec/dummy/public/favicon.ico +0 -0
  271. data/spec/execution_logger/cloud_watch_logs_spec.rb +95 -0
  272. data/spec/factories/execution_factory.rb +13 -0
  273. data/spec/factories/job_definition_factory.rb +21 -0
  274. data/spec/factories/job_instance_factory.rb +4 -0
  275. data/spec/factories/job_schedule_factory.rb +10 -0
  276. data/spec/factories/job_suspend_schedule_factory.rb +8 -0
  277. data/spec/factories/memory_expectancy_factory.rb +5 -0
  278. data/spec/factories/process_signal_factory.rb +4 -0
  279. data/spec/factories/star_factory.rb +4 -0
  280. data/spec/factories/tick_factory.rb +4 -0
  281. data/spec/factories/token_factory.rb +10 -0
  282. data/spec/factories/user_factory.rb +11 -0
  283. data/spec/factories/worker_factory.rb +8 -0
  284. data/spec/features/dashborad_spec.rb +82 -0
  285. data/spec/features/job_definition_spec.rb +74 -0
  286. data/spec/features/job_instance_spec.rb +94 -0
  287. data/spec/features/sign_in_and_out_spec.rb +17 -0
  288. data/spec/features/users_spec.rb +90 -0
  289. data/spec/features/workers_spec.rb +44 -0
  290. data/spec/helpers/executions_helper_spec.rb +4 -0
  291. data/spec/helpers/job_definition_helper_spec.rb +42 -0
  292. data/spec/helpers/job_schedules_helper_spec.rb +4 -0
  293. data/spec/helpers/logs_helper_spec.rb +4 -0
  294. data/spec/helpers/tokens_helper_spec.rb +4 -0
  295. data/spec/helpers/users_helper_spec.rb +4 -0
  296. data/spec/helpers/workers_helper_spec.rb +4 -0
  297. data/spec/mailers/notifications_spec.rb +54 -0
  298. data/spec/memory_sampler_spec.rb +11 -0
  299. data/spec/models/admin_assignment_spec.rb +4 -0
  300. data/spec/models/execution_spec.rb +26 -0
  301. data/spec/models/job_definition_spec.rb +163 -0
  302. data/spec/models/job_instance_spec.rb +115 -0
  303. data/spec/models/job_schedule_spec.rb +121 -0
  304. data/spec/models/job_suspend_schedule_spec.rb +32 -0
  305. data/spec/models/memory_consumption_log_spec.rb +50 -0
  306. data/spec/models/memory_expectancy_spec.rb +26 -0
  307. data/spec/models/star_spec.rb +4 -0
  308. data/spec/models/tick_spec.rb +23 -0
  309. data/spec/models/token_spec.rb +54 -0
  310. data/spec/models/user_spec.rb +17 -0
  311. data/spec/models/worker_spec.rb +5 -0
  312. data/spec/rails_helper.rb +81 -0
  313. data/spec/requests/api/job_instances_spec.rb +96 -0
  314. data/spec/requests/api/stats_spec.rb +45 -0
  315. data/spec/return_to_validator_spec.rb +28 -0
  316. data/spec/settings_spec.rb +10 -0
  317. data/spec/spec_helper.rb +49 -0
  318. data/spec/support/feature_sign_in_helper.rb +31 -0
  319. data/spec/support/sign_in_helper.rb +5 -0
  320. data/spec/support/wait_for_ajax.rb +11 -0
  321. data/spec/workflow/engine_spec.rb +241 -0
  322. data/spec/workflow/node_spec.rb +62 -0
  323. data/spec/workflow/notifier/hipchat_spec.rb +117 -0
  324. data/spec/workflow/notifier/mail_spec.rb +86 -0
  325. data/spec/workflow/notifier/slack_spec.rb +110 -0
  326. data/spec/workflow/script_parser_spec.rb +119 -0
  327. data/spec/workflow/shell_scanner_spec.rb +47 -0
  328. data/spec/workflow/task/auto_skip_error_spec.rb +35 -0
  329. data/spec/workflow/task/env_spec.rb +47 -0
  330. data/spec/workflow/task/execute_spec.rb +127 -0
  331. data/spec/workflow/task/expected_time_spec.rb +52 -0
  332. data/spec/workflow/task/fork_spec.rb +30 -0
  333. data/spec/workflow/task/queue_spec.rb +45 -0
  334. data/spec/workflow/task/rails_env_spec.rb +30 -0
  335. data/spec/workflow/task/sleep_spec.rb +22 -0
  336. data/spec/workflow/task/sub_process_spec.rb +32 -0
  337. data/spec/workflow/task/wait_spec.rb +162 -0
  338. metadata +1038 -0
@@ -0,0 +1,67 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>The page you were looking for doesn't exist (404)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/404.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>The page you were looking for doesn't exist.</h1>
62
+ <p>You may have mistyped the address or the page may have moved.</p>
63
+ </div>
64
+ <p>If you are the application owner check the logs for more information.</p>
65
+ </div>
66
+ </body>
67
+ </html>
@@ -0,0 +1,67 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>The change you wanted was rejected (422)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/422.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>The change you wanted was rejected.</h1>
62
+ <p>Maybe you tried to change something you didn't have access to.</p>
63
+ </div>
64
+ <p>If you are the application owner check the logs for more information.</p>
65
+ </div>
66
+ </body>
67
+ </html>
@@ -0,0 +1,66 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>We're sorry, but something went wrong (500)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/500.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>We're sorry, but something went wrong.</h1>
62
+ </div>
63
+ <p>If you are the application owner check the logs for more information.</p>
64
+ </div>
65
+ </body>
66
+ </html>
File without changes
File without changes
@@ -0,0 +1,95 @@
1
+ require 'rails_helper'
2
+
3
+ describe Kuroko2::ExecutionLogger::CloudWatchLogs do
4
+ let(:stream_name) { 'test' }
5
+ let(:object) { described_class.new(stream_name: stream_name, group_name: 'kuroko') }
6
+
7
+ describe '#put_logs' do
8
+ let(:events) { [{ timestamp: Time.now.to_i * 1000, message: 'hello' }] }
9
+ let(:response) { double('Response', data: { next_sequence_token: 'abc' })}
10
+
11
+ let(:send_parameters) do
12
+ {
13
+ log_group_name: 'kuroko',
14
+ log_stream_name: stream_name,
15
+ log_events: events,
16
+ sequence_token: nil,
17
+ }
18
+ end
19
+
20
+ it "sends logs to cloud watch logs" do
21
+ expect(object.client).to receive(:put_log_events).
22
+ with(send_parameters).and_return(response)
23
+ expect(object.put_logs(events)).to eq(response)
24
+ end
25
+
26
+ context 'when token is invalid' do
27
+ before do
28
+ exception = Aws::CloudWatchLogs::Errors::InvalidSequenceTokenException.new(
29
+ '',
30
+ 'The given sequenceToken is invalid. The next expected sequenceToken is: xxxx',
31
+ )
32
+
33
+ allow(object.client).to receive(:put_log_events).
34
+ with(send_parameters).and_raise(exception)
35
+ end
36
+
37
+ it 'gets token from the error message and retry' do
38
+ expect(object.client).to receive(:put_log_events).with(
39
+ log_group_name: 'kuroko',
40
+ log_stream_name: stream_name,
41
+ log_events: events,
42
+ sequence_token: 'xxxx',
43
+ ).and_return(response)
44
+
45
+ expect(object.put_logs(events)).to eq(response)
46
+ end
47
+ end
48
+
49
+ context 'when the stream is not created' do
50
+ before do
51
+ exception = Aws::CloudWatchLogs::Errors::ResourceNotFoundException.new('', '')
52
+ allow(object.client).to receive(:put_log_events).
53
+ with(send_parameters).and_raise(exception)
54
+ end
55
+
56
+ it 'creates the stream' do
57
+ expect(object.client).to receive(:create_log_stream).with(
58
+ log_group_name: 'kuroko',
59
+ log_stream_name: stream_name,
60
+ ) do
61
+ allow(object.client).to receive(:put_log_events).with(send_parameters).
62
+ and_return(response)
63
+ end
64
+
65
+ expect(object.put_logs(events)).to eq(response)
66
+ end
67
+ end
68
+ end
69
+
70
+ describe '#get_logs' do
71
+ let(:next_token) { 'next_token' }
72
+ let(:response) { double('Response', next_forward_token: next_token)}
73
+ let(:response2) { double('Response', next_forward_token: 'next_token2')}
74
+
75
+ it "gets logs" do
76
+ expect(object.client).to receive(:get_log_events).with({
77
+ log_group_name: 'kuroko',
78
+ log_stream_name: stream_name,
79
+ next_token: nil,
80
+ start_from_head: true,
81
+ }).and_return(response)
82
+
83
+ expect(object.get_logs).to eq(response)
84
+
85
+ expect(object.client).to receive(:get_log_events).with({
86
+ log_group_name: 'kuroko',
87
+ log_stream_name: stream_name,
88
+ next_token: next_token,
89
+ start_from_head: true,
90
+ }).and_return(response2)
91
+
92
+ expect(object.get_logs).to eq(response2)
93
+ end
94
+ end
95
+ end
@@ -0,0 +1,13 @@
1
+ FactoryGirl.define do
2
+ factory :execution, class: Kuroko2::Execution do
3
+ shell 'echo $NAME'
4
+ exit_status 0
5
+
6
+ job_definition { token.job_definition if token }
7
+ job_instance { token.job_instance if token }
8
+ context { token.context if token }
9
+
10
+ started_at { Time.now }
11
+ finished_at { Time.now }
12
+ end
13
+ end
@@ -0,0 +1,21 @@
1
+ FactoryGirl.define do
2
+ factory :job_definition, class: Kuroko2::JobDefinition do
3
+ name 'Job Definition'
4
+ description 'This is description for the job definition.'
5
+ script "noop:\n"
6
+ admins { build_list(:user, 1) }
7
+ prevent_multi false
8
+ memory_expectancy { create_memory_expectancy! }
9
+
10
+ factory :job_definition_with_instances do
11
+ transient do
12
+ job_instances_count 1
13
+ job_instances_token_status Kuroko2::Token::WORKING
14
+ end
15
+
16
+ after(:create) do |job_definition, evaluator|
17
+ create_list(:job_instance, evaluator.job_instances_count, job_definition: job_definition)
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,4 @@
1
+ FactoryGirl.define do
2
+ factory :job_instance, class: Kuroko2::JobInstance do
3
+ end
4
+ end
@@ -0,0 +1,10 @@
1
+ FactoryGirl.define do
2
+ factory :job_schedule, class: Kuroko2::JobSchedule do
3
+ sequence(:cron) do |n|
4
+ hour = n > 60 ? (n / 60) : '*'
5
+ day = n > 60 * 24 ? n / 60 % 24 : '*'
6
+
7
+ "#{n % 60} #{hour} #{day} * *"
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,8 @@
1
+ FactoryGirl.define do
2
+ factory :job_suspend_schedule, class: Kuroko2::JobSuspendSchedule do
3
+ sequence(:cron) do |n|
4
+ hour = n / 60 >= 1 ? (n / 60) : '*'
5
+ "#{n % 60} #{hour} * * *"
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,5 @@
1
+ FactoryGirl.define do
2
+ factory :memory_expectancy, class: Kuroko2::MemoryExpectancy do
3
+ expected_value 10
4
+ end
5
+ end
@@ -0,0 +1,4 @@
1
+ FactoryGirl.define do
2
+ factory :process_signal, class: Kuroko2::ProcessSignal do
3
+ end
4
+ end
@@ -0,0 +1,4 @@
1
+ FactoryGirl.define do
2
+ factory :star, class: Kuroko2::Star do
3
+ end
4
+ end
@@ -0,0 +1,4 @@
1
+ FactoryGirl.define do
2
+ factory :tick, class: Kuroko2::Tick do
3
+ end
4
+ end
@@ -0,0 +1,10 @@
1
+ FactoryGirl.define do
2
+ factory :token, class: Kuroko2::Token do
3
+ uuid { SecureRandom.uuid }
4
+ path '/'
5
+ script 'execute:'
6
+ context { Hash.new }
7
+
8
+ job_definition { job_instance.job_definition if job_instance }
9
+ end
10
+ end
@@ -0,0 +1,11 @@
1
+ FactoryGirl.define do
2
+ factory :user, class: Kuroko2::User do
3
+ sequence(:uid) { |n| "#{n}" }
4
+
5
+ name { "Alice Pleasance Liddell #{uid}" }
6
+ email { "#{uid}@example.com" }
7
+ first_name 'Alice'
8
+ last_name 'Liddell'
9
+ image 'http://example.com/alice/image'
10
+ end
11
+ end
@@ -0,0 +1,8 @@
1
+ FactoryGirl.define do
2
+ factory :worker, class: Kuroko2::Worker do
3
+ hostname "localhost"
4
+ sequence(:worker_id)
5
+ queue "@default"
6
+ working true
7
+ end
8
+ end
@@ -0,0 +1,82 @@
1
+ require 'rails_helper'
2
+
3
+ RSpec.describe "User shows dashboard", type: :feature do
4
+ let(:user) { create(:user) }
5
+
6
+ before do
7
+ sign_in(user)
8
+ end
9
+
10
+ context 'Favorite Jobs exists' do
11
+ let(:job_definition) { create(:job_definition) }
12
+
13
+ before do
14
+ create(:star, job_definition: job_definition, user: user)
15
+ end
16
+
17
+ it 'shows favorite jobs' do
18
+ visit kuroko2_path
19
+ expect(page).to have_content(job_definition.name)
20
+ expect(page).to have_selector('#definitions_list table tbody tr', count: 1)
21
+
22
+ expect(page).to have_content('There are no working jobs.')
23
+ end
24
+
25
+ context 'if the favorite job is working' do
26
+ before do
27
+ job_definition.job_instances.create
28
+ end
29
+
30
+ it 'shows working jobs' do
31
+ visit kuroko2_path
32
+ expect(page).not_to have_content('There are no working jobs.')
33
+ expect(page).to have_selector('#instances div table tr', count: 2)
34
+ end
35
+ end
36
+ end
37
+
38
+ context 'Some favorite jobs have tags', js: true do
39
+ let(:common_tag) { 'common_tag' }
40
+
41
+ before do
42
+ 10.times.each do |i|
43
+ create(
44
+ :star,
45
+ job_definition: create(:job_definition).tap { |d|
46
+ d.text_tags = "#{common_tag}, tag_#{i}"
47
+ d.save!
48
+ },
49
+ user: user
50
+ )
51
+ end
52
+ end
53
+
54
+ it 'shows tags' do
55
+ visit kuroko2_path
56
+ expect(page).to have_content(common_tag)
57
+ 10.times.each do |i|
58
+ expect(page).to have_content("tag_#{i}")
59
+ end
60
+
61
+ expect(page).to have_selector('#definitions_list table tbody tr', count: 10)
62
+ end
63
+
64
+ it 'selects tagged jobs' do
65
+ visit kuroko2_path
66
+
67
+ expect(page).to have_content(common_tag)
68
+
69
+ click_on(common_tag)
70
+ wait_for_ajax
71
+ expect(page).to have_selector('#definitions_list table tbody tr', count: 10)
72
+
73
+ click_on("tag_1")
74
+ wait_for_ajax
75
+ expect(page).to have_selector('#definitions_list table tbody tr', count: 1)
76
+
77
+ click_on("tag_1")
78
+ wait_for_ajax
79
+ expect(page).to have_selector('#definitions_list table tbody tr', count: 10)
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,74 @@
1
+ require 'rails_helper'
2
+
3
+ RSpec.describe "Management job definitions", type: :feature do
4
+ let(:user) { create(:user) }
5
+
6
+ before do
7
+ sign_in(user)
8
+ end
9
+
10
+ it 'creates/edit/destroy job_definition', js: true do
11
+ visit kuroko2.root_path
12
+
13
+ within '.sidebar-menu' do
14
+ click_on 'Create New'
15
+ end
16
+
17
+ fill_in 'job_definition_name', with: 'test1'
18
+ fill_in 'job_definition_description', with: 'description'
19
+ fill_in 'job_definition_script', with: 'noop:'
20
+ fill_in 'job_definition_text_tags', with: 'tag_1, common_tag'
21
+
22
+ click_on 'Create Job definition'
23
+
24
+ expect(page).to have_content('Job Definition Details')
25
+ expect(page).to have_content('test1')
26
+
27
+ click_on 'Edit Job definition'
28
+
29
+ fill_in 'job_definition_name', with: 'test1-edit'
30
+ click_on 'Update Job definition'
31
+
32
+ expect(page).to have_content('Job Definition Details')
33
+ expect(page).to have_content('test1-edit')
34
+
35
+ click_on 'Destroy Job definition'
36
+ expect(page).to have_content('All Job Definitions')
37
+ end
38
+
39
+ it 'add/delete job schedules', js: true do
40
+ visit kuroko2.root_path
41
+
42
+ within '.sidebar-menu' do
43
+ click_on 'Create New'
44
+ end
45
+
46
+ fill_in 'job_definition_name', with: 'test1'
47
+ fill_in 'job_definition_description', with: 'description'
48
+ fill_in 'job_definition_script', with: 'noop:'
49
+ fill_in 'job_definition_text_tags', with: 'tag_1, common_tag'
50
+
51
+ click_on 'Create Job definition'
52
+
53
+ expect(page).to have_content('Job Definition Details')
54
+ expect(page).to have_content('test1')
55
+
56
+ fill_in 'job_schedule_cron', with: '* * * * *'
57
+ click_on 'Add Schedule'
58
+ expect(page).to have_selector('#schedules table tbody tr .log', text: '* * * * *', count: 1)
59
+
60
+ within '#schedules' do
61
+ click_on 'Delete'
62
+ end
63
+ expect(page).to have_selector('#schedules table tbody tr .log', text: '* * * * *', count: 0)
64
+
65
+ fill_in 'job_suspend_schedule_cron', with: '* * * * *'
66
+ click_on 'Add Suspend Schedule'
67
+ expect(page).to have_selector('#suspend-schedules table tbody tr .log', text: '* * * * *', count: 1)
68
+
69
+ within '#suspend-schedules' do
70
+ click_on 'Delete'
71
+ end
72
+ expect(page).to have_selector('#suspend-schedules table tbody tr .log', text: '* * * * *', count: 0)
73
+ end
74
+ end
@@ -0,0 +1,94 @@
1
+ require 'rails_helper'
2
+
3
+ RSpec.describe "Launches a job instace and Management job instances on the web console", type: :feature do
4
+ let(:user) { create(:user) }
5
+ let(:job_definition) do
6
+ create(:job_definition).tap do |d|
7
+ d.admins << user
8
+ d.save!
9
+ end
10
+ end
11
+
12
+ let(:token) { job_definition.job_instances.first.tokens.first }
13
+ let(:workflow) { Kuroko2::Workflow::Engine.new }
14
+
15
+ before do
16
+ sign_in(user)
17
+ end
18
+
19
+ it 'launches jobs and shows the instance status', js: true do
20
+ visit kuroko2.job_definition_path(job_definition)
21
+
22
+ expect(page).to have_content('Job Definition Details')
23
+ expect(page).to have_content(job_definition.name)
24
+ click_on 'Launch'
25
+
26
+ expect(page).to have_selector('#launchAdHocModal .modal-dialog', visible: true)
27
+ within '#launchAdHocModal .modal-dialog' do
28
+ click_on 'Launch'
29
+ end
30
+
31
+ expect(page).to have_content('Job Instance Details')
32
+ expect(page).to have_selector('#instance-status .label', text: 'WORKING')
33
+
34
+ visit kuroko2.working_job_instances_path
35
+ expect(page).to have_content(job_definition.name)
36
+ expect(page).to have_selector('table.table tbody tr', count: 2)
37
+
38
+ visit kuroko2.job_definition_job_instance_path(job_definition, job_definition.job_instances.first)
39
+ until token.status == Kuroko2::Token::FINISHED
40
+ workflow.process(token)
41
+ end
42
+
43
+ sleep(2) # wait for setInterval, 2000
44
+ expect(page).to have_selector('#instance-status .label', text: 'SUCCESS')
45
+ end
46
+
47
+ context 'if error occurred' do
48
+ before do
49
+ job_definition.job_instances.create
50
+ workflow.process(token)
51
+ token.job_instance.touch(:error_at)
52
+ token.mark_as_failure
53
+ token.save!
54
+ end
55
+
56
+ it 'skips the token', js: true do
57
+ visit kuroko2.job_definition_job_instance_path(job_definition, job_definition.job_instances.first)
58
+ expect(page).to have_selector('#instance-status .label', text: 'ERROR')
59
+
60
+ click_on('Skip')
61
+
62
+ sleep(2) # wait for setInterval, 2000
63
+ expect(page).to have_selector('#instance-status .label', text: 'SUCCESS')
64
+ end
65
+
66
+
67
+ it 'retries the token', js: true do
68
+ visit kuroko2.job_definition_job_instance_path(job_definition, job_definition.job_instances.first)
69
+ expect(page).to have_selector('#instance-status .label', text: 'ERROR')
70
+
71
+ click_on('Retry')
72
+ token.reload
73
+
74
+ until token.status == Kuroko2::Token::FINISHED
75
+ workflow.process(token)
76
+ end
77
+
78
+ sleep(2) # wait for setInterval, 2000
79
+ expect(page).to have_selector('#instance-status .label', text: 'SUCCESS')
80
+ end
81
+
82
+ it 'cancels the instance', js: true do
83
+ visit kuroko2.job_definition_job_instance_path(job_definition, job_definition.job_instances.first)
84
+ expect(page).to have_selector('#instance-status .label', text: 'ERROR')
85
+
86
+ within '#instance' do
87
+ click_on('Cancel')
88
+ end
89
+
90
+ sleep(2) # wait for setInterval, 2000
91
+ expect(page).to have_selector('#instance-status .label', text: 'CANCEL')
92
+ end
93
+ end
94
+ end