firefighter-incident 0.0.14__tar.gz → 0.0.16__tar.gz

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 (509) hide show
  1. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/PKG-INFO +1 -1
  2. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/_version.py +2 -2
  3. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/serializers.py +9 -0
  4. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/signals/incident_updated.py +2 -2
  5. firefighter_incident-0.0.16/firefighter/incidents/enums.py +52 -0
  6. firefighter_incident-0.0.16/firefighter/incidents/forms/closure_reason.py +45 -0
  7. firefighter_incident-0.0.16/firefighter/incidents/forms/unified_incident.py +406 -0
  8. firefighter_incident-0.0.16/firefighter/incidents/forms/update_status.py +122 -0
  9. firefighter_incident-0.0.16/firefighter/incidents/migrations/0027_add_closure_fields.py +40 -0
  10. firefighter_incident-0.0.16/firefighter/incidents/migrations/0028_add_closure_reason_constraint.py +33 -0
  11. firefighter_incident-0.0.16/firefighter/incidents/migrations/0029_add_custom_fields_to_incident.py +22 -0
  12. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident.py +32 -5
  13. firefighter_incident-0.0.16/firefighter/incidents/static/css/main.min.css +1 -0
  14. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/status_pill.html +1 -1
  15. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/reports.py +3 -3
  16. firefighter_incident-0.0.16/firefighter/raid/apps.py +38 -0
  17. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/client.py +2 -2
  18. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/forms.py +75 -238
  19. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/signals/incident_created.py +38 -13
  20. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/signals/incident_updated.py +3 -2
  21. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/messages/slack_messages.py +19 -4
  22. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/rules.py +1 -1
  23. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/create_incident_conversation.py +6 -0
  24. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/incident_updated.py +7 -1
  25. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/__init__.py +4 -0
  26. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/form_utils.py +63 -0
  27. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/close.py +15 -2
  28. firefighter_incident-0.0.16/firefighter/slack/views/modals/closure_reason.py +193 -0
  29. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/open.py +60 -13
  30. firefighter_incident-0.0.16/firefighter/slack/views/modals/opening/details/unified.py +203 -0
  31. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/select_impact.py +1 -1
  32. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/set_details.py +3 -2
  33. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/postmortem.py +10 -2
  34. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/update_status.py +28 -2
  35. firefighter_incident-0.0.16/firefighter/slack/views/modals/utils.py +51 -0
  36. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_enums.py +100 -0
  37. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/conftest.py +179 -0
  38. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_closure_reason.py +91 -0
  39. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_unified_incident_form.py +570 -0
  40. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_unified_incident_form_integration.py +581 -0
  41. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_unified_incident_form_p4_p5.py +410 -0
  42. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_update_status_workflow.py +343 -0
  43. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_forms/test_workflow_transitions.py +167 -0
  44. firefighter_incident-0.0.16/firefighter_tests/test_incidents/test_models/test_incident_model.py +98 -0
  45. firefighter_incident-0.0.16/firefighter_tests/test_raid/conftest.py +154 -0
  46. firefighter_incident-0.0.16/firefighter_tests/test_raid/test_p1_p3_jira_fields.py +372 -0
  47. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_forms.py +10 -253
  48. firefighter_incident-0.0.16/firefighter_tests/test_raid/test_raid_signals.py +187 -0
  49. firefighter_incident-0.0.16/firefighter_tests/test_slack/messages/__init__.py +0 -0
  50. firefighter_incident-0.0.16/firefighter_tests/test_slack/messages/test_slack_messages.py +367 -0
  51. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/conftest.py +140 -0
  52. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/views/modals/test_close.py +65 -3
  53. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/test_closure_reason_modal.py +138 -0
  54. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/test_form_utils_multiple_choice.py +249 -0
  55. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/test_open.py +285 -0
  56. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/test_opening_unified.py +421 -0
  57. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/views/modals/test_update_status.py +327 -3
  58. firefighter_incident-0.0.16/firefighter_tests/test_slack/views/modals/test_utils.py +135 -0
  59. firefighter_incident-0.0.14/firefighter/incidents/enums.py +0 -32
  60. firefighter_incident-0.0.14/firefighter/incidents/forms/update_status.py +0 -36
  61. firefighter_incident-0.0.14/firefighter/incidents/static/css/main.min.css +0 -1
  62. firefighter_incident-0.0.14/firefighter/raid/apps.py +0 -55
  63. firefighter_incident-0.0.14/firefighter/raid/views/open_normal.py +0 -139
  64. firefighter_incident-0.0.14/firefighter/slack/views/modals/opening/details/critical.py +0 -88
  65. firefighter_incident-0.0.14/firefighter_tests/test_incidents/test_models/test_incident_model.py +0 -30
  66. firefighter_incident-0.0.14/firefighter_tests/test_slack/views/modals/test_open.py +0 -141
  67. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/.gitignore +0 -0
  68. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/LICENSE +0 -0
  69. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/README.md +0 -0
  70. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/__init__.py +0 -0
  71. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/__init__.py +0 -0
  72. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/admin.py +0 -0
  73. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/apps.py +0 -0
  74. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/authentication.py +0 -0
  75. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/migrations/0001_initial.py +0 -0
  76. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/migrations/0002_alter_apitokenproxy_options.py +0 -0
  77. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/migrations/0003_alter_apitokenproxy_options.py +0 -0
  78. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/migrations/__init__.py +0 -0
  79. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/models.py +0 -0
  80. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/permissions.py +0 -0
  81. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/renderer.py +0 -0
  82. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/urls.py +0 -0
  83. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/__init__.py +0 -0
  84. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/_base.py +0 -0
  85. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/components.py +0 -0
  86. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/environments.py +0 -0
  87. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/groups.py +0 -0
  88. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/incident_cost_types.py +0 -0
  89. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/incident_costs.py +0 -0
  90. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/incidents.py +0 -0
  91. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/api/views/severities.py +0 -0
  92. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/__init__.py +0 -0
  93. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/avatar/__init__.py +0 -0
  94. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/avatar/avatar.html +0 -0
  95. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/avatar/avatar.py +0 -0
  96. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/card/__init__.py +0 -0
  97. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/card/card.html +0 -0
  98. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/card/card.py +0 -0
  99. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/export_button/__init__.py +0 -0
  100. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/export_button/export_button.html +0 -0
  101. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/export_button/export_button.py +0 -0
  102. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form/__init__.py +0 -0
  103. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form/form.html +0 -0
  104. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form/form.py +0 -0
  105. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form_field/__init__.py +0 -0
  106. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form_field/form_field.html +0 -0
  107. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/form_field/form_field.py +0 -0
  108. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/messages/__init__.py +0 -0
  109. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/messages/messages.html +0 -0
  110. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/messages/messages.py +0 -0
  111. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/modal/__init__.py +0 -0
  112. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/modal/modal.html +0 -0
  113. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/components/modal/modal.py +0 -0
  114. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/__init__.py +0 -0
  115. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/admin.py +0 -0
  116. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/apps.py +0 -0
  117. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/client.py +0 -0
  118. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/__init__.py +0 -0
  119. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/commands/__init__.py +0 -0
  120. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/commands/sort_postmortems.py +0 -0
  121. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/commands/sort_runbooks.py +0 -0
  122. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/commands/sync_postmortems.py +0 -0
  123. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/management/commands/sync_runbooks.py +0 -0
  124. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/migrations/0001_initial_oss.py +0 -0
  125. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/migrations/__init__.py +0 -0
  126. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/models.py +0 -0
  127. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/serializers.py +0 -0
  128. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/service.py +0 -0
  129. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/signals/__init__.py +0 -0
  130. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tables.py +0 -0
  131. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/__init__.py +0 -0
  132. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/archive_postmortems.py +0 -0
  133. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/sort_runbooks.py +0 -0
  134. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/sync_pages_content.py +0 -0
  135. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/sync_postmortems.py +0 -0
  136. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/tasks/sync_runbooks.py +0 -0
  137. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/templates/oncall_team.xml +0 -0
  138. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/templates/pages/runbook_list.html +0 -0
  139. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/urls.py +0 -0
  140. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/utils.py +0 -0
  141. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/__init__.py +0 -0
  142. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/api.py +0 -0
  143. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/postmortem/__init__.py +0 -0
  144. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/postmortem/postmortem_detail.py +0 -0
  145. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/runbook/__init__.py +0 -0
  146. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/confluence/views/runbook/runbook_list.py +0 -0
  147. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/__init__.py +0 -0
  148. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/admin.py +0 -0
  149. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/apps.py +0 -0
  150. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/asgi.py +0 -0
  151. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/celery_client.py +0 -0
  152. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/fields_forms_widgets.py +0 -0
  153. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/filters.py +0 -0
  154. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/formats/__init__.py +0 -0
  155. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/formats/en/__init__.py +0 -0
  156. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/formats/en/formats.py +0 -0
  157. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/http_client.py +0 -0
  158. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/management/__init__.py +0 -0
  159. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/management/commands/__init__.py +0 -0
  160. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/management/commands/task.py +0 -0
  161. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/middleware.py +0 -0
  162. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/__init__.py +0 -0
  163. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/__init__.py +0 -0
  164. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/api.py +0 -0
  165. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/caches.py +0 -0
  166. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/celery.py +0 -0
  167. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/common.py +0 -0
  168. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/confluence.py +0 -0
  169. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/jira_app.py +0 -0
  170. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/logging.py +0 -0
  171. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/pagerduty.py +0 -0
  172. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/raid.py +0 -0
  173. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/components/slack.py +0 -0
  174. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/environments/__init__.py +0 -0
  175. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/environments/dev.py +0 -0
  176. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/environments/prod.py +0 -0
  177. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/settings_builder.py +0 -0
  178. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/settings/settings_utils.py +0 -0
  179. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/sso.py +0 -0
  180. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/tables_utils.py +0 -0
  181. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/templates/admin/base.html +0 -0
  182. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/templates/admin/login.html +0 -0
  183. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/templates/admin/send_message_conversation.html +0 -0
  184. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/templates/robots.txt +0 -0
  185. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/urls.py +0 -0
  186. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/utils.py +0 -0
  187. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/views.py +0 -0
  188. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/firefighter/wsgi.py +0 -0
  189. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/__init__.py +0 -0
  190. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/admin.py +0 -0
  191. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/apps.py +0 -0
  192. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/factories.py +0 -0
  193. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/__init__.py +0 -0
  194. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/close_incident.py +0 -0
  195. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/create_incident.py +0 -0
  196. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/edit.py +0 -0
  197. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/select_impact.py +0 -0
  198. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/update_key_events.py +0 -0
  199. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/update_roles.py +0 -0
  200. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/forms/utils.py +0 -0
  201. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/menus.py +0 -0
  202. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0001_initial_oss.py +0 -0
  203. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0002_alter_severity_name_alter_user_password_featureteam.py +0 -0
  204. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0003_delete_featureteam.py +0 -0
  205. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0004_incidentupdate_environment.py +0 -0
  206. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0005_enable_from_p1_to_p5_priority.py +0 -0
  207. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0006_update_group_names.py +0 -0
  208. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0007_update_component_name.py +0 -0
  209. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0008_impact_level.py +0 -0
  210. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0009_update_sla.py +0 -0
  211. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0010_update_components.py +0 -0
  212. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0011_update_incidents.py +0 -0
  213. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0012_alter_impactlevel.py +0 -0
  214. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0013_add_missing_component.py +0 -0
  215. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0014_update_components_slack_groups.py +0 -0
  216. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0015_update_impact_level.py +0 -0
  217. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0016_update_business_incidents_and_level.py +0 -0
  218. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0017_reorder_impact_types.py +0 -0
  219. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0018_update_impactlevel_names.py +0 -0
  220. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0019_set_security_components_private.py +0 -0
  221. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0020_create_incident_category_model.py +0 -0
  222. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0021_copy_component_data_to_incident_category.py +0 -0
  223. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0022_add_incident_category_fields.py +0 -0
  224. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0023_populate_incident_category_references.py +0 -0
  225. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0024_remove_component_fields_and_model.py +0 -0
  226. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0025_make_incident_category_required.py +0 -0
  227. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/0026_alter_incidentcategory_options_and_more.py +0 -0
  228. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/migrations/__init__.py +0 -0
  229. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/__init__.py +0 -0
  230. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/environment.py +0 -0
  231. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/group.py +0 -0
  232. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/impact.py +0 -0
  233. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_category.py +0 -0
  234. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_cost.py +0 -0
  235. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_cost_type.py +0 -0
  236. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_membership.py +0 -0
  237. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_role_type.py +0 -0
  238. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/incident_update.py +0 -0
  239. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/metric_type.py +0 -0
  240. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/milestone_type.py +0 -0
  241. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/priority.py +0 -0
  242. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/severity.py +0 -0
  243. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/models/user.py +0 -0
  244. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/signals.py +0 -0
  245. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/css/incident.css +0 -0
  246. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/css/main.css +0 -0
  247. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/css/tailwind.css +0 -0
  248. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/android-chrome-192x192.png +0 -0
  249. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/android-chrome-512x512.png +0 -0
  250. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/apple-touch-icon.png +0 -0
  251. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/favicon-16x16.png +0 -0
  252. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/favicon-32x32.png +0 -0
  253. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/favicon.ico +0 -0
  254. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/favicon/site.webmanifest +0 -0
  255. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/gameday.png +0 -0
  256. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/logo-firefighter.png +0 -0
  257. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/p1.png +0 -0
  258. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/p2.png +0 -0
  259. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/p3.png +0 -0
  260. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/p4.png +0 -0
  261. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/img/p5.png +0 -0
  262. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/js/main.js +0 -0
  263. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/static/js/main.min.js +0 -0
  264. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/tables.py +0 -0
  265. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/tasks/__init__.py +0 -0
  266. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/tasks/updateoncall.py +0 -0
  267. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/errors/base.html +0 -0
  268. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/filter.html +0 -0
  269. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/table/priority_column.html +0 -0
  270. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/table/status_column.html +0 -0
  271. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/table.html +0 -0
  272. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/widgets/form_container.html +0 -0
  273. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/widgets/grouped_checkbox_nested.html +0 -0
  274. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/incidents/widgets/input_option.html +0 -0
  275. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/index.html +0 -0
  276. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/created_at_help.html +0 -0
  277. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/environment_pill.html +0 -0
  278. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/footer.html +0 -0
  279. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/header.html +0 -0
  280. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/incident_card.html +0 -0
  281. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/incident_metrics.html +0 -0
  282. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/incident_timeline.html +0 -0
  283. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/incident_update_key_events_view.html +0 -0
  284. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/incident_update_key_events_view_modal.html +0 -0
  285. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/partial_table_list_paginated.html +0 -0
  286. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/priority_icon.html +0 -0
  287. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/priority_pill.html +0 -0
  288. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/table.html +0 -0
  289. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/user_card.html +0 -0
  290. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/partials/user_tooltip.html +0 -0
  291. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/layouts/view_filters.html +0 -0
  292. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/dashboard.html +0 -0
  293. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/docs_metrics.html +0 -0
  294. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_category_detail.html +0 -0
  295. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_category_list.html +0 -0
  296. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_create.html +0 -0
  297. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_detail.html +0 -0
  298. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_list.html +0 -0
  299. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_role_types_detail.html +0 -0
  300. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_role_types_list.html +0 -0
  301. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_statistics.html +0 -0
  302. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_statistics_partial.html +0 -0
  303. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/incident_update_key_events_form.html +0 -0
  304. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/templates/pages/user_detail.html +0 -0
  305. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/urls.py +0 -0
  306. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/__init__.py +0 -0
  307. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/components/__init__.py +0 -0
  308. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/components/details.py +0 -0
  309. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/components/list.py +0 -0
  310. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/date_filter.py +0 -0
  311. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/date_utils.py +0 -0
  312. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/docs/__init__.py +0 -0
  313. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/docs/metrics.py +0 -0
  314. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/docs/role_types.py +0 -0
  315. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/errors.py +0 -0
  316. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/users/__init__.py +0 -0
  317. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/users/details.py +0 -0
  318. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/incidents/views/views.py +0 -0
  319. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/__init__.py +0 -0
  320. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/admin.py +0 -0
  321. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/apps.py +0 -0
  322. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/client.py +0 -0
  323. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/migrations/0001_initial_oss.py +0 -0
  324. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/migrations/__init__.py +0 -0
  325. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/models.py +0 -0
  326. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/tasks/__init__.py +0 -0
  327. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/tasks/sync_users_jira.py +0 -0
  328. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/types.py +0 -0
  329. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/jira_app/utils.py +0 -0
  330. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/logging/__init__.py +0 -0
  331. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/logging/custom_json_formatter.py +0 -0
  332. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/logging/pretty_formatter.py +0 -0
  333. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/__init__.py +0 -0
  334. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/admin.py +0 -0
  335. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/apps.py +0 -0
  336. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/client.py +0 -0
  337. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/forms/__init__.py +0 -0
  338. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/forms/create_pagerduty_incident.py +0 -0
  339. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/migrations/0001_initial_oss.py +0 -0
  340. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/migrations/__init__.py +0 -0
  341. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/models.py +0 -0
  342. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/service.py +0 -0
  343. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/signals/__init__.py +0 -0
  344. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/signals/get_invites_from_pagerduty.py +0 -0
  345. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/signals/incident_channel_done_oncall.py +0 -0
  346. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/tasks/__init__.py +0 -0
  347. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/tasks/fetch_oncall.py +0 -0
  348. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/tasks/fetch_services.py +0 -0
  349. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/tasks/fetch_users.py +0 -0
  350. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/tasks/trigger_oncall.py +0 -0
  351. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/templates/pages/oncall_list.html +0 -0
  352. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/templates/pages/oncall_trigger.html +0 -0
  353. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/templates/partials/trigger_oncall_form_view.html +0 -0
  354. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/templates/partials/trigger_oncall_form_view_modal.html +0 -0
  355. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/urls.py +0 -0
  356. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/views/__init__.py +0 -0
  357. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/views/oncall_list.py +0 -0
  358. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/pagerduty/views/oncall_trigger.py +0 -0
  359. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/__init__.py +0 -0
  360. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/admin.py +0 -0
  361. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/messages.py +0 -0
  362. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/migrations/0001_initial_oss.py +0 -0
  363. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/migrations/0002_featureteam_remove_qualifierrotation_jira_user_and_more.py +0 -0
  364. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/migrations/0003_delete_raidarea.py +0 -0
  365. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/migrations/__init__.py +0 -0
  366. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/models.py +0 -0
  367. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/resources.py +0 -0
  368. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/serializers.py +0 -0
  369. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/service.py +0 -0
  370. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/signals/__init__.py +0 -0
  371. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/tasks/__init__.py +0 -0
  372. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/types.py +0 -0
  373. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/urls.py +0 -0
  374. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/utils.py +0 -0
  375. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/raid/views/__init__.py +0 -0
  376. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/__init__.py +0 -0
  377. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/admin.py +0 -0
  378. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/apps.py +0 -0
  379. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/factories.py +0 -0
  380. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/forms/__init__.py +0 -0
  381. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/forms/sos_form.py +0 -0
  382. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/management/__init__.py +0 -0
  383. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/management/commands/__init__.py +0 -0
  384. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/management/commands/generate_manifest.py +0 -0
  385. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/management/commands/switch_test_users.py +0 -0
  386. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/messages/__init__.py +0 -0
  387. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/messages/base.py +0 -0
  388. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0001_initial_oss.py +0 -0
  389. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0002_usergroup_tag.py +0 -0
  390. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0003_alter_usergroup_tag.py +0 -0
  391. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0004_alter_usergroup_components.py +0 -0
  392. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0005_add_incident_categories_fields.py +0 -0
  393. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0006_copy_components_to_incident_categories.py +0 -0
  394. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0007_remove_components_fields.py +0 -0
  395. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/0008_alter_conversation_incident_categories_and_more.py +0 -0
  396. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/migrations/__init__.py +0 -0
  397. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/__init__.py +0 -0
  398. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/conversation.py +0 -0
  399. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/incident_channel.py +0 -0
  400. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/message.py +0 -0
  401. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/sos.py +0 -0
  402. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/user.py +0 -0
  403. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/models/user_group.py +0 -0
  404. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/__init__.py +0 -0
  405. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/get_users.py +0 -0
  406. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/handle_incident_channel_done.py +0 -0
  407. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/incident_closed.py +0 -0
  408. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/postmortem_created.py +0 -0
  409. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/signals/roles_reminders.py +0 -0
  410. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/slack_app.py +0 -0
  411. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/slack_incident_context.py +0 -0
  412. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/slack_templating.py +0 -0
  413. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/__init__.py +0 -0
  414. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/fetch_conversations_members.py +0 -0
  415. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/reminder_postmortem.py +0 -0
  416. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/send_message.py +0 -0
  417. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/send_reminders.py +0 -0
  418. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/sync_users.py +0 -0
  419. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/update_usergroups_members.py +0 -0
  420. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/tasks/update_users.py +0 -0
  421. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/urls.py +0 -0
  422. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/utils.py +0 -0
  423. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/__init__.py +0 -0
  424. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/__init__.py +0 -0
  425. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/actions_and_shortcuts.py +0 -0
  426. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_archive.py +0 -0
  427. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_id_changed.py +0 -0
  428. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_rename.py +0 -0
  429. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_shared.py +0 -0
  430. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_unarchive.py +0 -0
  431. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/channel_unshared.py +0 -0
  432. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/commands.py +0 -0
  433. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/home.py +0 -0
  434. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/member_joined_channel.py +0 -0
  435. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/member_left_channel.py +0 -0
  436. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/message.py +0 -0
  437. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/message_deleted.py +0 -0
  438. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/events/reaction_added.py +0 -0
  439. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/__init__.py +0 -0
  440. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/base.py +0 -0
  441. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/base_mixins.py +0 -0
  442. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/mixins.py +0 -0
  443. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/base_modal/modal_utils.py +0 -0
  444. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/downgrade_workflow.py +0 -0
  445. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/edit.py +0 -0
  446. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/key_event_message.py +0 -0
  447. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/__init__.py +0 -0
  448. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/check_current_incidents.py +0 -0
  449. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/details/__init__.py +0 -0
  450. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/opening/types.py +0 -0
  451. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/select.py +0 -0
  452. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/send_sos.py +0 -0
  453. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/status.py +0 -0
  454. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/trigger_oncall.py +0 -0
  455. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/update.py +0 -0
  456. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/modals/update_roles.py +0 -0
  457. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter/slack/views/views.py +0 -0
  458. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/environments.json +0 -0
  459. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/groups.json +0 -0
  460. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/impact_level.json +0 -0
  461. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/impact_type.json +0 -0
  462. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/incident_categories.json +0 -0
  463. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/incident_role_type.json +0 -0
  464. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/metric_type.json +0 -0
  465. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/milestone_type.json +0 -0
  466. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/priorities.json +0 -0
  467. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_fixtures/incidents/severities.json +0 -0
  468. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/__init__.py +0 -0
  469. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/conftest.py +0 -0
  470. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_api/test_api_landbot.py +0 -0
  471. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_api/test_api_urls.py +0 -0
  472. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_confluence/test_confluence_utils.py +0 -0
  473. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_firefighter/test_firefighter_utils.py +0 -0
  474. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_firefighter/test_logging.py +0 -0
  475. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_firefighter/test_sso.py +0 -0
  476. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_firefighter/test_urls.py +0 -0
  477. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_forms/test_form_select_impact.py +0 -0
  478. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_forms/test_form_utils.py +0 -0
  479. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_forms/test_update_key_events.py +0 -0
  480. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_incident_urls.py +0 -0
  481. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_models/test_incident_category.py +0 -0
  482. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_models/test_migrations/test_incident_migrations.py +0 -0
  483. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_utils/test_date_utils.py +0 -0
  484. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_views/test_incident_detail_view.py +0 -0
  485. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_incidents/test_views/test_index_view.py +0 -0
  486. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_priority_mapping.py +0 -0
  487. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_client.py +0 -0
  488. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_client_users.py +0 -0
  489. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_models.py +0 -0
  490. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_serializers.py +0 -0
  491. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_service.py +0 -0
  492. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_transitions.py +0 -0
  493. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_utils.py +0 -0
  494. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_raid/test_raid_views.py +0 -0
  495. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/conftest.py +0 -0
  496. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/test_models/test_conversations.py +0 -0
  497. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/test_models/test_incident_channel.py +0 -0
  498. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/test_models/test_slack_user.py +0 -0
  499. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/test_slack_utils.py +0 -0
  500. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/views/modals/test_send_sos.py +0 -0
  501. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/firefighter_tests/test_slack/views/modals/test_status.py +0 -0
  502. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/gunicorn.conf.py +0 -0
  503. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/main.py +0 -0
  504. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/manage.py +0 -0
  505. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/package-lock.json +0 -0
  506. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/package.json +0 -0
  507. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/pyproject.toml +0 -0
  508. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/scripts/gen_credits.py +0 -0
  509. {firefighter_incident-0.0.14 → firefighter_incident-0.0.16}/scripts/hatch_build.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: firefighter-incident
3
- Version: 0.0.14
3
+ Version: 0.0.16
4
4
  Summary: Incident Management tool made for Slack using Django
5
5
  Project-URL: Repository, https://github.com/ManoManoTech/firefighter-incident
6
6
  Project-URL: Documentation, https://manomanotech.github.io/firefighter-incident/latest/
@@ -28,7 +28,7 @@ version_tuple: VERSION_TUPLE
28
28
  commit_id: COMMIT_ID
29
29
  __commit_id__: COMMIT_ID
30
30
 
31
- __version__ = version = '0.0.14'
32
- __version_tuple__ = version_tuple = (0, 0, 14)
31
+ __version__ = version = '0.0.16'
32
+ __version_tuple__ = version_tuple = (0, 0, 16)
33
33
 
34
34
  __commit_id__ = commit_id = None
@@ -218,6 +218,7 @@ class IncidentSerializer(TaggitSerializer, serializers.ModelSerializer[Incident]
218
218
  status = serializers.SerializerMethodField()
219
219
  created_by = UserSerializer(read_only=True)
220
220
  slack_channel_name = serializers.SerializerMethodField()
221
+ postmortem_url = serializers.SerializerMethodField()
221
222
 
222
223
  created_by_email = CreatableSlugRelatedField[User](
223
224
  source="created_by",
@@ -252,6 +253,13 @@ class IncidentSerializer(TaggitSerializer, serializers.ModelSerializer[Incident]
252
253
  def get_slack_channel_name(obj: Incident) -> str:
253
254
  return f"#{obj.slack_channel_name}" if obj.slack_channel_name else ""
254
255
 
256
+ @staticmethod
257
+ def get_postmortem_url(obj: Incident) -> str | None:
258
+ """Return the Confluence post-mortem page URL if it exists."""
259
+ if hasattr(obj, "postmortem_for"):
260
+ return obj.postmortem_for.page_url
261
+ return None
262
+
255
263
  def create(self, validated_data: dict[str, Any]) -> Incident:
256
264
  return Incident.objects.declare(**validated_data)
257
265
 
@@ -279,6 +287,7 @@ class IncidentSerializer(TaggitSerializer, serializers.ModelSerializer[Incident]
279
287
  "status",
280
288
  "slack_channel_name",
281
289
  "status_page_url",
290
+ "postmortem_url",
282
291
  "status",
283
292
  "environment_id",
284
293
  "incident_category_id",
@@ -39,7 +39,7 @@ def incident_updated_handler(
39
39
  if (
40
40
  "_status" in updated_fields
41
41
  and incident_update.status
42
- in {IncidentStatus.FIXED, IncidentStatus.POST_MORTEM}
42
+ in {IncidentStatus.MITIGATED, IncidentStatus.POST_MORTEM}
43
43
  and incident.needs_postmortem
44
44
  ):
45
45
  if not hasattr(incident, "postmortem_for"):
@@ -48,7 +48,7 @@ def incident_updated_handler(
48
48
  elif (
49
49
  "_status" in updated_fields
50
50
  and incident_update.status
51
- in {IncidentStatus.FIXED, IncidentStatus.POST_MORTEM}
51
+ in {IncidentStatus.MITIGATED, IncidentStatus.POST_MORTEM}
52
52
  and not incident.needs_postmortem
53
53
  ):
54
54
  publish_fixed_next_actions(incident)
@@ -0,0 +1,52 @@
1
+ from __future__ import annotations
2
+
3
+ from django.db import models
4
+
5
+
6
+ class IncidentStatus(models.IntegerChoices):
7
+ OPEN = 10, "Open"
8
+ INVESTIGATING = 20, "Investigating"
9
+ MITIGATING = 30, "Mitigating"
10
+ MITIGATED = 40, "Mitigated"
11
+ POST_MORTEM = 50, "Post-mortem"
12
+ CLOSED = 60, "Closed"
13
+
14
+ @staticmethod
15
+ def lt(val: int) -> list[IncidentStatus]:
16
+ return [i for i in IncidentStatus if i.value < val]
17
+
18
+ @staticmethod
19
+ def lte(val: int) -> list[IncidentStatus]:
20
+ return [i for i in IncidentStatus if i.value <= val]
21
+
22
+ @staticmethod
23
+ def gt(val: int) -> list[IncidentStatus]:
24
+ return [i for i in IncidentStatus if i.value > val]
25
+
26
+ @staticmethod
27
+ def gte(val: int) -> list[IncidentStatus]:
28
+ return [i for i in IncidentStatus if i.value >= val]
29
+
30
+ @staticmethod
31
+ def choices_lt(val: int) -> list[tuple[int, str]]:
32
+ return [i for i in IncidentStatus.choices if i[0] < val]
33
+
34
+ @staticmethod
35
+ def choices_lte(val: int) -> list[tuple[int, str]]:
36
+ return [i for i in IncidentStatus.choices if i[0] <= val]
37
+
38
+ @staticmethod
39
+ def choices_lte_skip_postmortem(val: int) -> list[tuple[int, str]]:
40
+ """Return choices up to val but excluding POST_MORTEM (for P3+ incidents)."""
41
+ return [i for i in IncidentStatus.choices if i[0] <= val and i[0] != IncidentStatus.POST_MORTEM]
42
+
43
+
44
+ class ClosureReason(models.TextChoices):
45
+ """Reasons for direct incident closure bypassing normal workflow."""
46
+
47
+ RESOLVED = "resolved", "Resolved normally"
48
+ DUPLICATE = "duplicate", "Duplicate incident"
49
+ FALSE_POSITIVE = "false_positive", "False alarm - no actual issue"
50
+ SUPERSEDED = "superseded", "Superseded by another incident"
51
+ EXTERNAL = "external", "External dependency/known issue"
52
+ CANCELLED = "cancelled", "Cancelled - no longer relevant"
@@ -0,0 +1,45 @@
1
+ """Form for incident closure with reason when closing from early statuses."""
2
+ from __future__ import annotations
3
+
4
+ from typing import TYPE_CHECKING, Any
5
+
6
+ from django import forms
7
+
8
+ from firefighter.incidents.enums import ClosureReason
9
+
10
+ if TYPE_CHECKING:
11
+ from firefighter.incidents.models import Incident
12
+
13
+
14
+ class IncidentClosureReasonForm(forms.Form):
15
+ """Form for closing an incident with a mandatory reason from early statuses."""
16
+
17
+ closure_reason = forms.ChoiceField(
18
+ label="Closure Reason",
19
+ choices=ClosureReason.choices,
20
+ required=True,
21
+ help_text="Select the reason for closing this incident",
22
+ )
23
+ closure_reference = forms.CharField(
24
+ label="Reference (optional)",
25
+ max_length=100,
26
+ required=False,
27
+ help_text="Reference incident ID or external link for context (e.g., #1234 or URL)",
28
+ )
29
+ message = forms.CharField(
30
+ label="Closure Message",
31
+ widget=forms.Textarea,
32
+ required=True,
33
+ help_text="Brief explanation of why this incident is being closed",
34
+ )
35
+
36
+ def __init__(self, *args: Any, incident: Incident | None = None, **kwargs: Any) -> None: # noqa: ARG002
37
+ super().__init__(*args, **kwargs)
38
+
39
+ # Exclude RESOLVED from choices as it's for normal workflow closure
40
+ closure_field = self.fields["closure_reason"]
41
+ if hasattr(closure_field, "choices"):
42
+ closure_field.choices = [
43
+ choice for choice in ClosureReason.choices
44
+ if choice[0] != ClosureReason.RESOLVED
45
+ ]
@@ -0,0 +1,406 @@
1
+ from __future__ import annotations
2
+
3
+ import logging
4
+ from typing import TYPE_CHECKING, Any
5
+ from typing import cast as typing_cast
6
+
7
+ from django import forms
8
+ from django.db import models
9
+
10
+ from firefighter.incidents.forms.create_incident import CreateIncidentFormBase
11
+ from firefighter.incidents.forms.select_impact import SelectImpactForm
12
+ from firefighter.incidents.forms.utils import GroupedModelChoiceField
13
+ from firefighter.incidents.models import Environment, IncidentCategory, Priority
14
+ from firefighter.incidents.models.impact import LevelChoices
15
+ from firefighter.incidents.models.incident import Incident
16
+ from firefighter.incidents.signals import create_incident_conversation
17
+
18
+ if TYPE_CHECKING:
19
+ from firefighter.incidents.models.impact import ImpactLevel
20
+ from firefighter.incidents.models.user import User
21
+ from firefighter.jira_app.models import JiraUser
22
+
23
+ logger = logging.getLogger(__name__)
24
+
25
+
26
+ class PlatformChoices(models.TextChoices):
27
+ """Platform choices for incidents."""
28
+
29
+ FR = "platform-FR", ":fr: FR"
30
+ DE = "platform-DE", ":de: DE"
31
+ IT = "platform-IT", ":it: IT"
32
+ ES = "platform-ES", ":es: ES"
33
+ UK = "platform-UK", ":uk: UK"
34
+ ALL = "platform-All", ":earth_africa: ALL"
35
+ INTERNAL = "platform-Internal", ":logo-manomano: Internal"
36
+
37
+
38
+ def initial_environments() -> list[Environment]:
39
+ """Get default environments."""
40
+ return list(Environment.objects.filter(default=True))
41
+
42
+
43
+ def initial_priority() -> Priority:
44
+ """Get default priority."""
45
+ return Priority.objects.get(default=True)
46
+
47
+
48
+ def initial_platform() -> str:
49
+ """Get default platform."""
50
+ return PlatformChoices.ALL.value
51
+
52
+
53
+ class UnifiedIncidentForm(CreateIncidentFormBase):
54
+ """Unified form for all incident types and priorities (P1-P5).
55
+
56
+ This form dynamically shows/hides fields based on:
57
+ - Priority/response_type (critical vs normal)
58
+ - Selected impacts (customer, seller, employee)
59
+
60
+ Common fields (always shown):
61
+ - title, description, incident_category
62
+ - environment (multiple choice)
63
+ - platform (multiple choice, default ALL)
64
+ - priority (hidden)
65
+
66
+ Conditional fields:
67
+ - suggested_team_routing (P4-P5 only)
68
+ - zendesk_ticket_id (if customer impact selected)
69
+ - seller_contract_id, is_key_account, etc. (if seller impact selected)
70
+ """
71
+
72
+ # === Common fields (ALL priorities) ===
73
+ title = forms.CharField(
74
+ label="Title",
75
+ max_length=128,
76
+ min_length=10,
77
+ widget=forms.TextInput(attrs={"placeholder": "What's going on?"}),
78
+ )
79
+
80
+ description = forms.CharField(
81
+ label="Summary",
82
+ widget=forms.Textarea(
83
+ attrs={
84
+ "placeholder": "Help people responding to the incident. This will be posted to #tech-incidents and on our internal status page.\nThis description can be edited later."
85
+ }
86
+ ),
87
+ min_length=10,
88
+ max_length=1200,
89
+ )
90
+
91
+ incident_category = GroupedModelChoiceField(
92
+ choices_groupby="group",
93
+ label="Incident category",
94
+ queryset=(
95
+ IncidentCategory.objects.all()
96
+ .select_related("group")
97
+ .order_by(
98
+ "group__order",
99
+ "name",
100
+ )
101
+ ),
102
+ )
103
+
104
+ environment = forms.ModelMultipleChoiceField(
105
+ label="Environment",
106
+ queryset=Environment.objects.all(),
107
+ initial=initial_environments,
108
+ required=True,
109
+ )
110
+
111
+ platform = forms.MultipleChoiceField(
112
+ label="Platform",
113
+ choices=PlatformChoices.choices,
114
+ initial=[PlatformChoices.ALL.value],
115
+ required=True,
116
+ )
117
+
118
+ priority = forms.ModelChoiceField(
119
+ label="Priority",
120
+ queryset=Priority.objects.filter(enabled_create=True),
121
+ initial=initial_priority,
122
+ widget=forms.HiddenInput(),
123
+ )
124
+
125
+ # === Conditional: Normal incidents only (P4-P5) ===
126
+ suggested_team_routing: forms.ModelChoiceField[Any] = forms.ModelChoiceField(
127
+ queryset=None, # Will be set in __init__
128
+ label="Feature Team or Train",
129
+ required=False, # Conditionally required based on response_type
130
+ )
131
+
132
+ # === Conditional: Customer impact ===
133
+ zendesk_ticket_id = forms.CharField(
134
+ label="Zendesk Ticket ID",
135
+ max_length=128,
136
+ min_length=2,
137
+ required=False,
138
+ )
139
+
140
+ # === Conditional: Seller impact ===
141
+ seller_contract_id = forms.CharField(
142
+ label="Seller Contract ID",
143
+ max_length=128,
144
+ min_length=0,
145
+ required=False, # Conditionally required in clean()
146
+ )
147
+
148
+ is_key_account = forms.BooleanField(
149
+ label="Is it a Key Account?",
150
+ required=False,
151
+ )
152
+
153
+ is_seller_in_golden_list = forms.BooleanField(
154
+ label="Is the seller in the Golden List?",
155
+ required=False,
156
+ )
157
+
158
+ zoho_desk_ticket_id = forms.CharField(
159
+ label="Zoho Desk Ticket ID",
160
+ max_length=128,
161
+ min_length=1,
162
+ required=False,
163
+ )
164
+
165
+ field_order = [
166
+ "incident_category",
167
+ "environment",
168
+ "platform",
169
+ "title",
170
+ "description",
171
+ "suggested_team_routing",
172
+ "zendesk_ticket_id",
173
+ "seller_contract_id",
174
+ "is_key_account",
175
+ "is_seller_in_golden_list",
176
+ "zoho_desk_ticket_id",
177
+ ]
178
+
179
+ def __init__(self, *args: Any, **kwargs: Any) -> None:
180
+ """Initialize form with dynamic queryset for suggested_team_routing."""
181
+ super().__init__(*args, **kwargs)
182
+
183
+ # Set queryset for suggested_team_routing
184
+ try:
185
+ from firefighter.raid.models import FeatureTeam # noqa: PLC0415
186
+
187
+ field = typing_cast("forms.ModelChoiceField[Any]", self.fields["suggested_team_routing"])
188
+ field.queryset = FeatureTeam.objects.only("name").order_by("name")
189
+ except ImportError:
190
+ # RAID module not available
191
+ logger.warning("RAID module not available, suggested_team_routing will not work")
192
+
193
+ def get_visible_fields_for_impacts(
194
+ self, impacts_data: dict[str, ImpactLevel | str], response_type: str
195
+ ) -> list[str]:
196
+ """Determine which fields should be visible based on impacts and response type.
197
+
198
+ Args:
199
+ impacts_data: Dictionary of impact type → impact level (ImpactLevel object or UUID string)
200
+ response_type: "critical" or "normal"
201
+
202
+ Returns:
203
+ List of field names that should be visible
204
+ """
205
+ visible_fields = [
206
+ "title",
207
+ "description",
208
+ "incident_category",
209
+ "environment",
210
+ "platform",
211
+ "priority",
212
+ ]
213
+
214
+ # Add suggested_team_routing for normal incidents (P4-P5)
215
+ if response_type == "normal":
216
+ visible_fields.append("suggested_team_routing")
217
+
218
+ # Check impact selections
219
+ customer_impact = None
220
+ seller_impact = None
221
+
222
+ for field_name, impact_level in impacts_data.items():
223
+ if "customers_impact" in field_name:
224
+ customer_impact = impact_level
225
+ elif "sellers_impact" in field_name:
226
+ seller_impact = impact_level
227
+
228
+ # Helper to check if impact is not NONE
229
+ def has_impact(impact: ImpactLevel | str | None) -> bool:
230
+ if impact is None:
231
+ return False
232
+
233
+ # If it's a UUID string, fetch the ImpactLevel from database
234
+ if isinstance(impact, str):
235
+ from firefighter.incidents.models.impact import ( # noqa: PLC0415
236
+ ImpactLevel as ImpactLevelModel,
237
+ )
238
+
239
+ try:
240
+ impact_obj = ImpactLevelModel.objects.get(id=impact)
241
+ except ImpactLevelModel.DoesNotExist:
242
+ return False
243
+ else:
244
+ return impact_obj.value != LevelChoices.NONE.value
245
+
246
+ # Otherwise it's an ImpactLevel object
247
+ return impact.value != LevelChoices.NONE.value
248
+
249
+ # Add customer-specific fields
250
+ if has_impact(customer_impact):
251
+ visible_fields.append("zendesk_ticket_id")
252
+
253
+ # Add seller-specific fields
254
+ if has_impact(seller_impact):
255
+ visible_fields.extend([
256
+ "seller_contract_id",
257
+ "is_key_account",
258
+ "is_seller_in_golden_list",
259
+ "zoho_desk_ticket_id",
260
+ ])
261
+
262
+ return visible_fields
263
+
264
+ def clean(self) -> dict[str, Any]:
265
+ """Custom validation based on response type and impacts."""
266
+ cleaned_data = super().clean()
267
+ if cleaned_data is None:
268
+ cleaned_data = {}
269
+
270
+ # Get response_type from initial data if available
271
+ initial = self.initial or {}
272
+ response_type = initial.get("response_type", "critical")
273
+
274
+ # Validate suggested_team_routing is required for normal incidents
275
+ if response_type == "normal" and not cleaned_data.get("suggested_team_routing"):
276
+ self.add_error(
277
+ "suggested_team_routing",
278
+ "Feature Team is required for P4/P5 incidents",
279
+ )
280
+
281
+ return cleaned_data
282
+
283
+ def trigger_incident_workflow(
284
+ self,
285
+ creator: User,
286
+ impacts_data: dict[str, ImpactLevel],
287
+ response_type: str = "critical",
288
+ *args: Any,
289
+ **kwargs: Any,
290
+ ) -> None:
291
+ """Trigger the appropriate incident workflow based on response type.
292
+
293
+ Args:
294
+ creator: User creating the incident
295
+ impacts_data: Dictionary of impact data
296
+ response_type: "critical" or "normal"
297
+ *args: Additional positional arguments (unused)
298
+ **kwargs: Additional keyword arguments (unused)
299
+ """
300
+ if response_type == "critical":
301
+ self._trigger_critical_incident_workflow(creator, impacts_data)
302
+ else:
303
+ self._trigger_normal_incident_workflow(creator, impacts_data)
304
+
305
+ def _trigger_critical_incident_workflow(
306
+ self,
307
+ creator: User,
308
+ impacts_data: dict[str, ImpactLevel],
309
+ ) -> None:
310
+ """Create a critical incident (P1-P3) with Slack channel."""
311
+ # Create incident with first environment only (critical incidents use single env)
312
+ cleaned_data_copy = self.cleaned_data.copy()
313
+ logger.info(f"UNIFIED FORM - cleaned_data keys: {list(self.cleaned_data.keys())}")
314
+ logger.info(f"UNIFIED FORM - cleaned_data values: {self.cleaned_data}")
315
+
316
+ environments = cleaned_data_copy.pop("environment", [])
317
+ platforms = cleaned_data_copy.pop("platform", [])
318
+
319
+ # Extract customer/seller fields for Jira ticket (not stored in Incident model)
320
+ jira_extra_fields = {
321
+ "suggested_team_routing": cleaned_data_copy.pop("suggested_team_routing", None),
322
+ "zendesk_ticket_id": cleaned_data_copy.pop("zendesk_ticket_id", None),
323
+ "seller_contract_id": cleaned_data_copy.pop("seller_contract_id", None),
324
+ "is_key_account": cleaned_data_copy.pop("is_key_account", None),
325
+ "is_seller_in_golden_list": cleaned_data_copy.pop("is_seller_in_golden_list", None),
326
+ "zoho_desk_ticket_id": cleaned_data_copy.pop("zoho_desk_ticket_id", None),
327
+ # Pass full lists for Jira ticket creation
328
+ "environments": [env.value for env in environments], # Convert QuerySet to list of values
329
+ "platforms": platforms, # Already a list of strings
330
+ }
331
+ logger.info(f"UNIFIED FORM - jira_extra_fields extracted: {jira_extra_fields}")
332
+
333
+ # Use first environment
334
+ if environments:
335
+ cleaned_data_copy["environment"] = environments[0]
336
+
337
+ # Store custom fields in the incident
338
+ cleaned_data_copy["custom_fields"] = {
339
+ k: v for k, v in jira_extra_fields.items() if v is not None
340
+ }
341
+
342
+ incident = Incident.objects.declare(created_by=creator, **cleaned_data_copy)
343
+ impacts_form = SelectImpactForm(impacts_data)
344
+ impacts_form.save(incident=incident)
345
+
346
+ create_incident_conversation.send(
347
+ "unified_incident_form",
348
+ incident=incident,
349
+ jira_extra_fields=jira_extra_fields,
350
+ impacts_data=impacts_data, # Pass impacts_data for business_impact computation
351
+ )
352
+
353
+ def _trigger_normal_incident_workflow(
354
+ self,
355
+ creator: User,
356
+ impacts_data: dict[str, ImpactLevel],
357
+ ) -> None:
358
+ """Create a normal incident (P4-P5) with Jira ticket only."""
359
+ from firefighter.raid.client import client as jira_client # noqa: PLC0415
360
+ from firefighter.raid.forms import ( # noqa: PLC0415
361
+ prepare_jira_fields,
362
+ process_jira_issue,
363
+ )
364
+ from firefighter.raid.service import ( # noqa: PLC0415
365
+ get_jira_user_from_user,
366
+ )
367
+
368
+ jira_user: JiraUser = get_jira_user_from_user(creator)
369
+
370
+ # Extract environments and platforms
371
+ environments_qs = self.cleaned_data.get("environment", [])
372
+ environments = [env.value for env in environments_qs] # Convert QuerySet to list of values
373
+ platforms = self.cleaned_data.get("platform", [])
374
+
375
+ # Extract suggested team routing (convert FeatureTeam instance to string)
376
+ team_routing = self.cleaned_data.get("suggested_team_routing")
377
+ team_routing_name = team_routing.name if team_routing else None
378
+
379
+ # Prepare all Jira fields using the common function
380
+ # P4-P5 pass all environments (unlike P1-P3 which pass first only)
381
+ jira_fields = prepare_jira_fields(
382
+ title=self.cleaned_data["title"],
383
+ description=self.cleaned_data["description"],
384
+ priority=self.cleaned_data["priority"].value,
385
+ reporter=jira_user.id,
386
+ incident_category=self.cleaned_data["incident_category"].name,
387
+ environments=environments, # ✅ P4-P5: pass ALL environments
388
+ platforms=platforms,
389
+ impacts_data=impacts_data,
390
+ optional_fields={
391
+ "zendesk_ticket_id": self.cleaned_data.get("zendesk_ticket_id", ""),
392
+ "seller_contract_id": self.cleaned_data.get("seller_contract_id", ""),
393
+ "zoho_desk_ticket_id": self.cleaned_data.get("zoho_desk_ticket_id", ""),
394
+ "is_key_account": self.cleaned_data.get("is_key_account"),
395
+ "is_seller_in_golden_list": self.cleaned_data.get("is_seller_in_golden_list"),
396
+ "suggested_team_routing": team_routing_name,
397
+ },
398
+ )
399
+
400
+ # Create Jira issue with all prepared fields
401
+ issue_data = jira_client.create_issue(**jira_fields)
402
+
403
+ # Process the created Jira ticket (create JiraTicket in DB, save impacts, alert Slack)
404
+ process_jira_issue(
405
+ issue_data, creator, jira_user=jira_user, impacts_data=impacts_data
406
+ )