cmdbsyncer 4.1.0.dev1__tar.gz → 4.1.0.dev3__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 (297) hide show
  1. {cmdbsyncer-4.1.0.dev1/cmdbsyncer.egg-info → cmdbsyncer-4.1.0.dev3}/PKG-INFO +1 -1
  2. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/auth/views.py +73 -27
  3. cmdbsyncer-4.1.0.dev3/application/buildinfo.txt +1 -0
  4. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v4.1.md +2 -1
  5. cmdbsyncer-4.1.0.dev3/application/themes/dracula.css +234 -0
  6. cmdbsyncer-4.1.0.dev3/application/themes/gruvbox-dark.css +241 -0
  7. cmdbsyncer-4.1.0.dev3/application/themes/gruvbox-light.css +207 -0
  8. cmdbsyncer-4.1.0.dev3/application/themes/nord.css +241 -0
  9. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3/cmdbsyncer.egg-info}/PKG-INFO +1 -1
  10. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/cmdbsyncer.egg-info/SOURCES.txt +4 -0
  11. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/pyproject.toml +2 -1
  12. cmdbsyncer-4.1.0.dev1/application/buildinfo.txt +0 -1
  13. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/LICENSE +0 -0
  14. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/README.md +0 -0
  15. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/__init__.py +0 -0
  16. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/_version.py +0 -0
  17. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/__init__.py +0 -0
  18. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/inventory.py +0 -0
  19. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/objects.py +0 -0
  20. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/rules.py +0 -0
  21. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/syncer.py +0 -0
  22. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/api/views.py +0 -0
  23. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/.pages +0 -0
  24. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.10.md +0 -0
  25. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.11.md +0 -0
  26. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.12.md +0 -0
  27. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.5.md +0 -0
  28. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.7.md +0 -0
  29. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.8.md +0 -0
  30. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v3.9.md +0 -0
  31. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/changelog/v4.0.md +0 -0
  32. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/cli.py +0 -0
  33. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/config.py +0 -0
  34. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/docu_links.py +0 -0
  35. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/enterprise.py +0 -0
  36. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/__init__.py +0 -0
  37. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/audit.py +0 -0
  38. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/cron.py +0 -0
  39. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/get_account.py +0 -0
  40. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/inventory.py +0 -0
  41. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/local_config_file.py +0 -0
  42. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/local_config_presets.py +0 -0
  43. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/mongo_keys.py +0 -0
  44. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/notification_channels.py +0 -0
  45. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/notification_dispatch.py +0 -0
  46. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/plugins.py +0 -0
  47. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/sates.py +0 -0
  48. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/sql.py +0 -0
  49. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/syncer_jinja.py +0 -0
  50. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/tablib_formater.py +0 -0
  51. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/tests/__init__.py +0 -0
  52. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/helpers/tests/test_sql.py +0 -0
  53. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/mcp_server.py +0 -0
  54. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/__init__.py +0 -0
  55. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/account.py +0 -0
  56. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/config.py +0 -0
  57. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/cron.py +0 -0
  58. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/field_approval.py +0 -0
  59. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/forms.py +0 -0
  60. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/host.py +0 -0
  61. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/host_inventory_tree.py +0 -0
  62. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/notification_channel.py +0 -0
  63. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/notification_rule.py +0 -0
  64. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/notification_state.py +0 -0
  65. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/saved_search.py +0 -0
  66. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/states.py +0 -0
  67. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/models/user.py +0 -0
  68. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/__init__.py +0 -0
  69. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/custom_attributes/models.py +0 -0
  70. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/custom_attributes/rules.py +0 -0
  71. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/custom_attributes/views.py +0 -0
  72. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/debug.py +0 -0
  73. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/email.py +0 -0
  74. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/inventory/__init__.py +0 -0
  75. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/log/log.py +0 -0
  76. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/log/models.py +0 -0
  77. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/log/views.py +0 -0
  78. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/plugin.py +0 -0
  79. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/__init__.py +0 -0
  80. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/filter.py +0 -0
  81. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/match.py +0 -0
  82. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/models.py +0 -0
  83. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/rewrite.py +0 -0
  84. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/rule.py +0 -0
  85. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/rule/views.py +0 -0
  86. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/modules/statefile.py +0 -0
  87. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/notices/strict_certificate_verification.txt +0 -0
  88. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/__init__.py +0 -0
  89. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/__init__.py +0 -0
  90. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/admin_views.py +0 -0
  91. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/inventory.py +0 -0
  92. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/models.py +0 -0
  93. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/playbook_rules.py +0 -0
  94. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/rules.py +0 -0
  95. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/runner.py +0 -0
  96. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/site_syncer.py +0 -0
  97. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ansible/views.py +0 -0
  98. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/bmc_remedy/__init__.py +0 -0
  99. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/bmc_remedy/bmc_remedy.py +0 -0
  100. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/__init__.py +0 -0
  101. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/admin_views.py +0 -0
  102. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/bi.py +0 -0
  103. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/cmk2.py +0 -0
  104. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/cmk_rules.py +0 -0
  105. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/dcd.py +0 -0
  106. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/downtimes.py +0 -0
  107. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/groups.py +0 -0
  108. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/helpers.py +0 -0
  109. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/import_v1.py +0 -0
  110. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/import_v2.py +0 -0
  111. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/inits.py +0 -0
  112. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/inventorize.py +0 -0
  113. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/models.py +0 -0
  114. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/notification_rules.py +0 -0
  115. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/passwords.py +0 -0
  116. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/poolfolder.py +0 -0
  117. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/rules.py +0 -0
  118. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/sites.py +0 -0
  119. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/syncer.py +0 -0
  120. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tags.py +0 -0
  121. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/__init__.py +0 -0
  122. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_bi.py +0 -0
  123. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_cmk2.py +0 -0
  124. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_cmk_rules.py +0 -0
  125. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_dcd.py +0 -0
  126. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_downtimes.py +0 -0
  127. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_groups.py +0 -0
  128. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_helpers.py +0 -0
  129. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_import_v1.py +0 -0
  130. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_import_v2.py +0 -0
  131. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_inventorize.py +0 -0
  132. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_notification_rules.py +0 -0
  133. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_passwords.py +0 -0
  134. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_poolfolder.py +0 -0
  135. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_rules.py +0 -0
  136. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_sites.py +0 -0
  137. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_syncer.py +0 -0
  138. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_tags.py +0 -0
  139. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/tests/test_users.py +0 -0
  140. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/users.py +0 -0
  141. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/checkmk/views.py +0 -0
  142. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/cisco_dna/__init__.py +0 -0
  143. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/cisco_dna/syncer.py +0 -0
  144. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/cron.py +0 -0
  145. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/csv/__init__.py +0 -0
  146. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/csv/csv.py +0 -0
  147. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/file_requests.py +0 -0
  148. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/__init__.py +0 -0
  149. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/admin_views.py +0 -0
  150. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/models.py +0 -0
  151. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/rules.py +0 -0
  152. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/syncer.py +0 -0
  153. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/idoit/views.py +0 -0
  154. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jdisc/__init__.py +0 -0
  155. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jdisc/applications.py +0 -0
  156. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jdisc/devices.py +0 -0
  157. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jdisc/executables.py +0 -0
  158. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jdisc/jdisc.py +0 -0
  159. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jira/__init__.py +0 -0
  160. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jira/jira.py +0 -0
  161. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jira_cloud/__init__.py +0 -0
  162. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/jira_cloud/jira_cloud.py +0 -0
  163. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/json/__init__.py +0 -0
  164. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/json/json.py +0 -0
  165. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ldap/__init__.py +0 -0
  166. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/ldap/ldap.py +0 -0
  167. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/maintenance/__init__.py +0 -0
  168. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/mssql/__init__.py +0 -0
  169. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/mysql/__init__.py +0 -0
  170. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/mysql/mysql.py +0 -0
  171. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/__init__.py +0 -0
  172. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/admin_views.py +0 -0
  173. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/cluster.py +0 -0
  174. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/contacts.py +0 -0
  175. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/dataflow.py +0 -0
  176. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/devices.py +0 -0
  177. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/interfaces.py +0 -0
  178. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/ips.py +0 -0
  179. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/models.py +0 -0
  180. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/netbox.py +0 -0
  181. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/networks.py +0 -0
  182. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/prefixes.py +0 -0
  183. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/rules.py +0 -0
  184. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/views.py +0 -0
  185. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/netbox/virtualmachines.py +0 -0
  186. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/prtg/__init__.py +0 -0
  187. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/prtg/prtg.py +0 -0
  188. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/pyodbc/__init__.py +0 -0
  189. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/pyodbc/pyodbc.py +0 -0
  190. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rest/__init__.py +0 -0
  191. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rest/rest.py +0 -0
  192. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/__init__.py +0 -0
  193. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/admin_views.py +0 -0
  194. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/autorules.py +0 -0
  195. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/models.py +0 -0
  196. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/rule_definitions.py +0 -0
  197. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/rule_import_export.py +0 -0
  198. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/rules/views.py +0 -0
  199. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/syncer_shell.py +0 -0
  200. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/__init__.py +0 -0
  201. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/admin_views.py +0 -0
  202. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/custom_attributes.py +0 -0
  203. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/models.py +0 -0
  204. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/rules.py +0 -0
  205. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/views.py +0 -0
  206. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/vmware/vmware.py +0 -0
  207. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/yml/__init__.py +0 -0
  208. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins/yml/yml.py +0 -0
  209. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/plugins_cli.py +0 -0
  210. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/static/css/cmdbsyncer.css +0 -0
  211. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/static/js/main.js +0 -0
  212. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/static/logo_white.png +0 -0
  213. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/_brand.html +0 -0
  214. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/_theme.html +0 -0
  215. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/_host_tabs.html +0 -0
  216. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/account_pick_type.html +0 -0
  217. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/ansible_playbook_run.html +0 -0
  218. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/ansible_project_detail.html +0 -0
  219. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/ansible_rule_list.html +0 -0
  220. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/bulk_label_form.html +0 -0
  221. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/changelog_archive.html +0 -0
  222. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/checkmk_rule_mngmt_list.html +0 -0
  223. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/checkmk_settings_list.html +0 -0
  224. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/copy_as_new_form.html +0 -0
  225. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/data_quality.html +0 -0
  226. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/file/list.html +0 -0
  227. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/file/modals/form.html +0 -0
  228. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_details.html +0 -0
  229. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_edit.html +0 -0
  230. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_inventory_tree.html +0 -0
  231. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_list.html +0 -0
  232. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_relations_graph.html +0 -0
  233. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/host_timeline.html +0 -0
  234. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/index.html +0 -0
  235. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/local_config_editor.html +0 -0
  236. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/master.html +0 -0
  237. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/model/clone_confirm.html +0 -0
  238. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/model/inline_list_base.html +0 -0
  239. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/object_list.html +0 -0
  240. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/set_cmk_version_form.html +0 -0
  241. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/admin/set_template_form.html +0 -0
  242. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/base.html +0 -0
  243. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/change_password.html +0 -0
  244. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/debug.html +0 -0
  245. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/debug_host.html +0 -0
  246. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/email/newuser.html +0 -0
  247. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/email/notification.html +0 -0
  248. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/email/resetpassword.html +0 -0
  249. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/formular.html +0 -0
  250. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/license_info.html +0 -0
  251. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/login.html +0 -0
  252. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/logout_confirm.html +0 -0
  253. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/request_password.html +0 -0
  254. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/set_2fa.html +0 -0
  255. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/templates/set_theme.html +0 -0
  256. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/themes_registry.py +0 -0
  257. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/_form_fields.py +0 -0
  258. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/_form_sections.py +0 -0
  259. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/account.py +0 -0
  260. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/config.py +0 -0
  261. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/cron.py +0 -0
  262. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/data_quality.py +0 -0
  263. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/default.py +0 -0
  264. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/field_approval.py +0 -0
  265. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/fileadmin.py +0 -0
  266. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/host.py +0 -0
  267. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/host_filters.py +0 -0
  268. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/host_renderers.py +0 -0
  269. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/host_widgets.py +0 -0
  270. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/license.py +0 -0
  271. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/notification_channel.py +0 -0
  272. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/notification_rule.py +0 -0
  273. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/saved_search.py +0 -0
  274. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/application/views/user.py +0 -0
  275. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/cmdbsyncer.egg-info/dependency_links.txt +0 -0
  276. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/cmdbsyncer.egg-info/entry_points.txt +0 -0
  277. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/cmdbsyncer.egg-info/requires.txt +0 -0
  278. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/cmdbsyncer.egg-info/top_level.txt +0 -0
  279. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/requirements-ansible.txt +0 -0
  280. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/requirements-extras.txt +0 -0
  281. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/requirements.txt +0 -0
  282. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/setup.cfg +0 -0
  283. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/syncerapi/__init__.py +0 -0
  284. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/syncerapi/v1/__init__.py +0 -0
  285. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/syncerapi/v1/core/__init__.py +0 -0
  286. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/syncerapi/v1/inventory/__init__.py +0 -0
  287. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/syncerapi/v1/rest/__init__.py +0 -0
  288. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_api.py +0 -0
  289. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_api_csrf_invariant.py +0 -0
  290. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_default_view.py +0 -0
  291. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_mongo_keys.py +0 -0
  292. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_plugin.py +0 -0
  293. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_plugin_ssti.py +0 -0
  294. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_plugins_cli.py +0 -0
  295. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_rule.py +0 -0
  296. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_rule_match.py +0 -0
  297. {cmdbsyncer-4.1.0.dev1 → cmdbsyncer-4.1.0.dev3}/tests/test_webhook_token_hash.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: cmdbsyncer
3
- Version: 4.1.0.dev1
3
+ Version: 4.1.0.dev3
4
4
  Summary: Rule-based modular synchronizer for Checkmk, Netbox, Ansible, I-DOIT, Jira CMDB and 15+ other CMDB/monitoring systems
5
5
  Author-email: Kuhn & Ruess GmbH <info@kuhn-ruess.de>
6
6
  Maintainer-email: Bastian Kuhn <mail@bastian-kuhn.de>
@@ -15,7 +15,7 @@ from joserfc.errors import JoseError
15
15
  from mongoengine.errors import DoesNotExist
16
16
 
17
17
  from application import login_manager, app, log, limiter
18
- from application.enterprise import run_hook
18
+ from application.enterprise import has_feature, run_hook
19
19
  from application.helpers.audit import audit
20
20
  from application.models.user import User
21
21
  from application.themes_registry import get_choices as theme_choices, is_known as theme_is_known
@@ -27,6 +27,29 @@ AUTH_RATE_LIMIT = app.config.get('AUTH_RATE_LIMIT', '3 per minute; 10 per hour')
27
27
  AUTH = Blueprint('auth', __name__)
28
28
 
29
29
 
30
+ def _dbg(message, **details):
31
+ """Write a Settings → Log entry only when AUTH_DEBUG is on.
32
+
33
+ ``Log.log`` expects ``details`` as a list of ``(key, value)`` pairs;
34
+ passing a dict makes ``_log_function`` iterate the keys as strings
35
+ and slice characters off them, which is why the entries used to
36
+ render as garbled single chars."""
37
+ if not app.config.get('AUTH_DEBUG'):
38
+ return
39
+ log.log(message, source='AUTH',
40
+ details=list(details.items()) if details else None)
41
+
42
+
43
+ def _candidate_remote_user_headers(req):
44
+ """Common reverse-proxy headers that *should* carry the user id when
45
+ REMOTE_USER itself is empty. Helps operators spot a misconfigured
46
+ Apache/nginx that forwards e.g. ``X-Forwarded-User`` instead of
47
+ setting the WSGI ``REMOTE_USER`` environ key."""
48
+ wanted = {'x-remote-user', 'x-forwarded-user',
49
+ 'remote-user', 'x-authenticated-user', 'x-auth-user'}
50
+ return {k: v for k, v in req.headers.items() if k.lower() in wanted} or None
51
+
52
+
30
53
  @AUTH.errorhandler(429)
31
54
  def ratelimit_handler(_error):
32
55
  """Generic message on rate-limit hit; details intentionally omitted."""
@@ -53,33 +76,56 @@ def login(): # pylint: disable=too-many-return-statements,too-many-branches,too
53
76
  flash('Already Logged in')
54
77
  return redirect(url_for("admin.index"))
55
78
 
56
- if app.config['REMOTE_USER_LOGIN'] and request.remote_user:
57
- try:
58
- existing_user = run_hook('remote_user', request)
59
- if existing_user:
60
- session.clear()
61
- login_user(
62
- existing_user,
63
- remember=False,
64
- duration=timedelta(
65
- hours=(current_app.config['ADMIN_SESSION_HOURS'] or 8)
79
+ if app.config['REMOTE_USER_LOGIN']:
80
+ _dbg('remote_user dispatcher: entry',
81
+ remote_user=request.remote_user or None,
82
+ has_remote_user=bool(request.remote_user),
83
+ remote_addr=request.remote_addr,
84
+ trusted_proxies=app.config.get('TRUSTED_PROXIES', 0),
85
+ enterprise_hook_registered=has_feature('remote_user'))
86
+ if not request.remote_user:
87
+ _dbg('remote_user dispatcher: REMOTE_USER_LOGIN is on, but '
88
+ 'the proxy did not pass REMOTE_USER',
89
+ remote_addr=request.remote_addr,
90
+ candidate_headers=_candidate_remote_user_headers(request))
91
+ else:
92
+ try:
93
+ existing_user = run_hook('remote_user', request)
94
+ if existing_user:
95
+ session.clear()
96
+ login_user(
97
+ existing_user,
98
+ remember=False,
99
+ duration=timedelta(
100
+ hours=(current_app.config['ADMIN_SESSION_HOURS'] or 8)
101
+ )
66
102
  )
67
- )
68
- existing_user.last_login = datetime.utcnow()
69
- existing_user.save()
70
- audit('user.login.success',
71
- actor_type='user',
72
- actor_id=str(existing_user.id),
73
- actor_name=existing_user.email,
74
- metadata={'method': 'remote_user'})
75
- return redirect(url_for("admin.index"))
76
- except Exception: # pylint: disable=broad-exception-caught
77
- log.log("Remote User login failed", source="AUTH")
78
- audit('user.login.failure', outcome='failure',
79
- actor_name=request.remote_user,
80
- metadata={'method': 'remote_user',
81
- 'reason': 'hook_exception'})
82
- flash('Remote User Error', 'danger')
103
+ existing_user.last_login = datetime.utcnow()
104
+ existing_user.save()
105
+ audit('user.login.success',
106
+ actor_type='user',
107
+ actor_id=str(existing_user.id),
108
+ actor_name=existing_user.email,
109
+ metadata={'method': 'remote_user'})
110
+ _dbg('remote_user dispatcher: login success',
111
+ remote_user=request.remote_user,
112
+ user_id=str(existing_user.id),
113
+ email=existing_user.email)
114
+ return redirect(url_for("admin.index"))
115
+ _dbg('remote_user dispatcher: hook returned no user — '
116
+ 'falling through to login form',
117
+ remote_user=request.remote_user,
118
+ enterprise_hook_registered=has_feature('remote_user'))
119
+ except Exception as exp: # pylint: disable=broad-exception-caught
120
+ log.log("Remote User login failed", source="AUTH")
121
+ _dbg('remote_user dispatcher: hook raised exception',
122
+ remote_user=request.remote_user,
123
+ error=f'{exp.__class__.__name__}: {exp}')
124
+ audit('user.login.failure', outcome='failure',
125
+ actor_name=request.remote_user,
126
+ metadata={'method': 'remote_user',
127
+ 'reason': 'hook_exception'})
128
+ flash('Remote User Error', 'danger')
83
129
 
84
130
 
85
131
  login_form = LoginForm(request.form)
@@ -0,0 +1 @@
1
+ BUILD_DATE=2026-05-08T12:05:04Z
@@ -82,6 +82,7 @@
82
82
  - FEAT: Drop a `.css` file into `plugins/themes/` to add your own theme to the picker
83
83
  - FEAT: Set Theme, Set 2FA and Change Password pages now keep the admin navigation
84
84
  - FIX: Settings → License menu entry is hidden on Community Edition installs (no enterprise package present), so admins are not pointed at a page with no upload form and an empty feature table
85
+ - FIX: PyPI installs ship the bundled theme CSS files (Gruvbox Dark / Light, Nord, Dracula) so the theme picker actually shows themes other than Default
85
86
 
86
87
  ### Plugin runtime
87
88
  - FIX: HTTP sessions and CA-cert temp files are released even when a plugin's init fails
@@ -90,7 +91,7 @@
90
91
  - FEAT: `cmdbsyncer sys self_configure` now creates a default `app.wsgi` so PyPI installs can be served by Apache/mod_wsgi or uWSGI without writing one by hand
91
92
  - FIX: `Edit local_config.py` GUI now writes to the same `local_config.py` Python actually imports. PyPI installs previously wrote into site-packages instead of the deployment directory next to `app.wsgi`
92
93
  - FEAT: Offline installation bundle always ships base, extras and ansible Python dependencies plus the default Ansible playbook collection, and the bundled `install.sh` deploys the playbooks to `/opt/cmdbsyncer/ansible` (override via `ANSIBLE_TARGET`, skip with `SKIP_ANSIBLE=1`, replace existing target with `FORCE=1`)
93
- - FEAT: New `make release-pre` target ships sequential pre-release builds (`.devN` / `aN` / `bN` / `rcN`) to PyPI without requiring a hand-edit before each upload; `tools/build_offline_bundle.sh --pre` lets the offline bundle pick those pre-releases up so QA can test them on air-gapped systems
94
+ - FEAT: New `make release-pre` target ships sequential pre-release builds (`.devN` / `aN` / `bN` / `rcN`) to PyPI without requiring a hand-edit before each upload; `tools/build_offline_bundle.sh --syncer-version 4.1.0.dev3 --enterprise-version 0.3.9.dev1` pins the offline bundle to those pre-releases so QA can test them on air-gapped systems
94
95
 
95
96
  ### Refactor
96
97
  - REFACTOR: `application/views/host.py` split into focused modules (widgets, filters, renderers)
@@ -0,0 +1,234 @@
1
+ /* @name: Dracula */
2
+ :root {
3
+ --nav-bg: #21222c;
4
+ --nav-link: #f8f8f2;
5
+ --cmk-group-bg: #bd93f9;
6
+ --cmk-group-bg-hover: #ff79c6;
7
+ --cmk-group-fg: #282a36;
8
+ --cmk-group-border: #44475a;
9
+ }
10
+ body, .main-container, .container, .container-fluid {
11
+ background-color: #282a36 !important;
12
+ color: #f8f8f2;
13
+ }
14
+ a { color: #8be9fd; }
15
+ a:hover, a:focus { color: #f1fa8c; }
16
+ h1, h2, h3, h4, h5, h6, label, legend, .form-text, p { color: #f8f8f2; }
17
+
18
+ .table, .model-list, .table.searchable, .table.table-bordered {
19
+ --bs-table-bg: #343746;
20
+ --bs-table-color: #f8f8f2;
21
+ --bs-table-striped-bg: #2e303e;
22
+ --bs-table-striped-color: #f8f8f2;
23
+ --bs-table-hover-bg: #44475a;
24
+ --bs-table-hover-color: #f1fa8c;
25
+ --bs-table-border-color: #44475a;
26
+ --bs-table-active-bg: #44475a;
27
+ --bs-table-active-color: #f1fa8c;
28
+ background-color: #343746 !important;
29
+ color: #f8f8f2 !important;
30
+ border-color: #44475a !important;
31
+ }
32
+ .table th, .table td,
33
+ .model-list th, .model-list td {
34
+ background-color: transparent !important;
35
+ color: #f8f8f2 !important;
36
+ border-color: #44475a !important;
37
+ }
38
+ .model-list thead th, .table thead th {
39
+ background-color: #44475a !important;
40
+ color: #f8f8f2 !important;
41
+ border-bottom-color: #6272a4 !important;
42
+ box-shadow: inset 0 -1px 0 #6272a4;
43
+ }
44
+ .table-striped > tbody > tr:nth-of-type(odd) > * {
45
+ background-color: #2e303e !important;
46
+ color: #f8f8f2 !important;
47
+ }
48
+ .table-hover > tbody > tr:hover > *,
49
+ .table.searchable tbody tr:hover > * {
50
+ background-color: #44475a !important;
51
+ color: #f1fa8c !important;
52
+ }
53
+ .table.searchable td:first-child {
54
+ background-color: #2e303e !important;
55
+ color: #bd93f9 !important;
56
+ }
57
+ .table-responsive {
58
+ border-color: #44475a;
59
+ box-shadow: 0 2px 6px rgba(0,0,0,0.45);
60
+ }
61
+
62
+ .table .fa, .table .fas, .table .far, .table .glyphicon,
63
+ .table a, .table a > i,
64
+ .model-list .fa, .model-list .fas, .model-list .glyphicon,
65
+ .model-list a, .model-list a > i {
66
+ color: #f8f8f2 !important;
67
+ }
68
+ .table a:hover, .table a:hover > i,
69
+ .table .fa:hover, .table .glyphicon:hover,
70
+ .model-list a:hover, .model-list a:hover > i {
71
+ color: #f1fa8c !important;
72
+ }
73
+ .icon-minus-sign, .fa-times, .fa-trash, .fa-remove { color: #ff5555 !important; }
74
+ .icon-ok-circle, .fa-check, .fa-ok { color: #50fa7b !important; }
75
+
76
+ .app-card, .card, fieldset.inline-field, .well, .panel,
77
+ .rule-section, .rule-section-body {
78
+ background-color: #343746 !important;
79
+ border-color: #44475a !important;
80
+ color: #f8f8f2 !important;
81
+ }
82
+ .rule-section-head {
83
+ background-color: #2e303e !important;
84
+ border-bottom-color: #44475a !important;
85
+ }
86
+ .rule-section-head h4, .rule-section-head p { color: #f8f8f2 !important; }
87
+
88
+ .form-control, .form-control:focus, .form-select,
89
+ select, textarea,
90
+ input[type=text], input[type=email], input[type=password],
91
+ input[type=number], input[type=search], input[type=url],
92
+ input[type=date], input[type=time], input[type=datetime-local] {
93
+ background-color: #21222c !important;
94
+ color: #f8f8f2 !important;
95
+ border-color: #44475a !important;
96
+ }
97
+ select option, .form-select option { background-color: #21222c; color: #f8f8f2; }
98
+ .form-control::placeholder { color: #6272a4; }
99
+
100
+ .dropdown-menu {
101
+ background-color: #343746 !important;
102
+ border-color: #44475a !important;
103
+ color: #f8f8f2 !important;
104
+ }
105
+ .dropdown-item, .dropdown-menu > li > a {
106
+ color: #f8f8f2 !important;
107
+ }
108
+ .dropdown-item:hover, .dropdown-item:focus,
109
+ .dropdown-menu > li > a:hover, .dropdown-menu > li > a:focus {
110
+ background-color: #44475a !important;
111
+ color: #f1fa8c !important;
112
+ }
113
+ .dropdown-divider, .dropdown-menu .divider { border-top-color: #44475a !important; background-color: #44475a !important; }
114
+ .dropdown-header { color: #6272a4 !important; }
115
+
116
+ .btn-default, .btn-secondary, .btn-light,
117
+ .btn-outline-secondary, .btn-outline-default {
118
+ background-color: #44475a !important;
119
+ border-color: #6272a4 !important;
120
+ color: #f8f8f2 !important;
121
+ }
122
+ .btn-default:hover, .btn-secondary:hover, .btn-light:hover,
123
+ .btn-outline-secondary:hover, .btn-outline-default:hover {
124
+ background-color: #6272a4 !important;
125
+ color: #f1fa8c !important;
126
+ }
127
+
128
+ .pagination .page-link {
129
+ background-color: #343746;
130
+ color: #f8f8f2;
131
+ border-color: #44475a;
132
+ }
133
+ .pagination .page-item.active .page-link {
134
+ background-color: #bd93f9;
135
+ border-color: #bd93f9;
136
+ color: #282a36;
137
+ }
138
+ .pagination .page-link:hover { background-color: #44475a; color: #f1fa8c; }
139
+
140
+ .modal-content { background-color: #343746 !important; color: #f8f8f2 !important; border-color: #44475a !important; }
141
+ .modal-header, .modal-footer { border-color: #44475a !important; }
142
+ .alert { background-color: #343746; color: #f8f8f2; border-color: #44475a; }
143
+
144
+ .filters .filter-op, .filters select, .filters input { background-color: #21222c !important; color: #f8f8f2 !important; border-color: #44475a !important; }
145
+
146
+ .home-hero { color: #f8f8f2 !important; border-bottom-color: #44475a !important; }
147
+ .home-hero h1, .home-hero p { color: #f8f8f2 !important; }
148
+ .home-hero .build-pill { background-color: #bd93f9 !important; color: #282a36 !important; }
149
+ .home-card {
150
+ background-color: #343746 !important;
151
+ border-color: #44475a !important;
152
+ color: #f8f8f2 !important;
153
+ box-shadow: 0 2px 6px rgba(0,0,0,0.45) !important;
154
+ }
155
+ .home-card h2, .home-card h4 { color: #f8f8f2 !important; border-bottom-color: #44475a !important; }
156
+ .links-list a { color: #8be9fd !important; }
157
+ .links-list a:hover { color: #f1fa8c !important; }
158
+ #changelog-content {
159
+ background-color: #2e303e !important;
160
+ border-color: #44475a !important;
161
+ color: #f8f8f2 !important;
162
+ }
163
+ #changelog-content details { border-left-color: #44475a !important; }
164
+ #changelog-content details[open] { border-left-color: #bd93f9 !important; }
165
+ #changelog-content summary.changelog-version::before { color: #6272a4 !important; }
166
+ #changelog-content details[open] > summary.changelog-version::before { color: #bd93f9 !important; }
167
+ #changelog-content .changelog-version-title { color: #f8f8f2 !important; }
168
+ #changelog-content details[open] > summary .changelog-version-title { color: #f1fa8c !important; }
169
+ .filter-chip { background-color: #2e303e !important; border-color: #44475a !important; color: #f8f8f2 !important; }
170
+ .filter-chip.active-feat { color: #8be9fd !important; border-color: #8be9fd !important; background-color: #21222c !important; }
171
+ .filter-chip.active-fix { color: #50fa7b !important; border-color: #50fa7b !important; background-color: #21222c !important; }
172
+ .filter-chip.active-inc { color: #ff5555 !important; border-color: #ff5555 !important; background-color: #21222c !important; }
173
+ .filter-chip.active-sec { color: #ffb86c !important; border-color: #ffb86c !important; background-color: #21222c !important; }
174
+ .filter-chip.active-oth { color: #6272a4 !important; border-color: #44475a !important; background-color: #21222c !important; }
175
+ .filter-toggle-all { background-color: #44475a !important; color: #f8f8f2 !important; }
176
+ .filter-toggle-all:hover { background-color: #6272a4 !important; }
177
+ .notice-box {
178
+ background-color: #343746 !important;
179
+ border-color: #ff79c6 !important;
180
+ border-left-color: #ff79c6 !important;
181
+ color: #f8f8f2 !important;
182
+ }
183
+ .notice-box .notice-confirm { background-color: #ff79c6 !important; color: #282a36 !important; }
184
+ .notice-box .notice-confirm:hover { background-color: #bd93f9 !important; }
185
+ .previous-releases a { background-color: #44475a !important; color: #f8f8f2 !important; }
186
+ .previous-releases a:hover { background-color: #6272a4 !important; color: #f1fa8c !important; }
187
+
188
+ /* Renderer-injected widgets. */
189
+ .cmdb-label-row,
190
+ .cmdb-inv-grid .cmdb-label-row { border-bottom-color: #44475a !important; }
191
+ .cmdb-label-row .lbl-val,
192
+ .cmdb-inv-grid .lbl-val { color: #f8f8f2 !important; }
193
+ .cmdb-inv-grid .lbl-src { background: #44475a !important; color: #f8f8f2 !important; }
194
+ .cmdb-log-list { background: #2e303e !important; border-color: #44475a !important; }
195
+ .cmdb-log-row { border-bottom-color: #44475a !important; }
196
+ .cmdb-log-row .log-msg { color: #f8f8f2 !important; }
197
+ .cmdb-log-row .log-ts,
198
+ .cmdb-log-meta { color: #6272a4 !important; }
199
+
200
+ /* Nav-tabs strip at the top of every Flask-Admin edit/detail page. */
201
+ .nav-tabs {
202
+ border-bottom-color: #44475a !important;
203
+ }
204
+ .nav-tabs .nav-link {
205
+ color: #f8f8f2 !important;
206
+ border-color: transparent !important;
207
+ }
208
+ .nav-tabs .nav-link:hover,
209
+ .nav-tabs .nav-link:focus {
210
+ color: #f1fa8c !important;
211
+ border-color: #44475a #44475a #44475a !important;
212
+ background-color: #343746 !important;
213
+ }
214
+ .nav-tabs .nav-link.active,
215
+ .nav-tabs .nav-item.show .nav-link {
216
+ background-color: #282a36 !important;
217
+ color: #f1fa8c !important;
218
+ border-color: #44475a #44475a #282a36 !important;
219
+ }
220
+
221
+ /* Theme-aware surface tokens — used by debug_host, _host_tabs,
222
+ ansible_project_detail, host_relations_graph, ansible_rule_list,
223
+ ansible_playbook_run and any future template that opts in via
224
+ var(--surface-*, fallback). */
225
+ :root {
226
+ --surface-bg: #282a36;
227
+ --surface-subtle: #343746;
228
+ --surface-border: #44475a;
229
+ --surface-divider: #44475a;
230
+ --surface-text: #f8f8f2;
231
+ --surface-muted: #6272a4;
232
+ --debug-key: #8be9fd;
233
+ --debug-row-hit: #2d4438;
234
+ }
@@ -0,0 +1,241 @@
1
+ /* @name: Gruvbox Dark */
2
+ :root {
3
+ --nav-bg: #1d2021;
4
+ --nav-link: #ebdbb2;
5
+ --cmk-group-bg: #504945;
6
+ --cmk-group-bg-hover: #665c54;
7
+ --cmk-group-fg: #fabd2f;
8
+ --cmk-group-border: #3c3836;
9
+ }
10
+ body, .main-container, .container, .container-fluid {
11
+ background-color: #282828 !important;
12
+ color: #ebdbb2;
13
+ }
14
+ a { color: #83a598; }
15
+ a:hover, a:focus { color: #fabd2f; }
16
+ h1, h2, h3, h4, h5, h6, label, legend, .form-text, p { color: #ebdbb2; }
17
+
18
+ .table, .model-list, .table.searchable, .table.table-bordered {
19
+ --bs-table-bg: #3c3836;
20
+ --bs-table-color: #ebdbb2;
21
+ --bs-table-striped-bg: #32302f;
22
+ --bs-table-striped-color: #ebdbb2;
23
+ --bs-table-hover-bg: #504945;
24
+ --bs-table-hover-color: #fabd2f;
25
+ --bs-table-border-color: #504945;
26
+ --bs-table-active-bg: #504945;
27
+ --bs-table-active-color: #fabd2f;
28
+ background-color: #3c3836 !important;
29
+ color: #ebdbb2 !important;
30
+ border-color: #504945 !important;
31
+ }
32
+ .table th, .table td,
33
+ .model-list th, .model-list td {
34
+ background-color: transparent !important;
35
+ color: #ebdbb2 !important;
36
+ border-color: #504945 !important;
37
+ }
38
+ .model-list thead th, .table thead th {
39
+ background-color: #504945 !important;
40
+ color: #ebdbb2 !important;
41
+ border-bottom-color: #665c54 !important;
42
+ box-shadow: inset 0 -1px 0 #665c54;
43
+ }
44
+ .table-striped > tbody > tr:nth-of-type(odd) > * {
45
+ background-color: #32302f !important;
46
+ color: #ebdbb2 !important;
47
+ }
48
+ .table-hover > tbody > tr:hover > *,
49
+ .table.searchable tbody tr:hover > * {
50
+ background-color: #504945 !important;
51
+ color: #fabd2f !important;
52
+ }
53
+ .table.searchable td:first-child {
54
+ background-color: #32302f !important;
55
+ color: #fabd2f !important;
56
+ }
57
+ .table-responsive {
58
+ border-color: #504945;
59
+ box-shadow: 0 2px 6px rgba(0,0,0,0.45);
60
+ }
61
+
62
+ .table .fa, .table .fas, .table .far, .table .glyphicon,
63
+ .table a, .table a > i,
64
+ .model-list .fa, .model-list .fas, .model-list .glyphicon,
65
+ .model-list a, .model-list a > i {
66
+ color: #ebdbb2 !important;
67
+ }
68
+ .table a:hover, .table a:hover > i,
69
+ .table .fa:hover, .table .glyphicon:hover,
70
+ .model-list a:hover, .model-list a:hover > i {
71
+ color: #fabd2f !important;
72
+ }
73
+ .icon-minus-sign, .fa-times, .fa-trash, .fa-remove { color: #fb4934 !important; }
74
+ .icon-ok-circle, .fa-check, .fa-ok { color: #b8bb26 !important; }
75
+
76
+ .app-card, .card, fieldset.inline-field, .well, .panel,
77
+ .rule-section, .rule-section-body {
78
+ background-color: #3c3836 !important;
79
+ border-color: #504945 !important;
80
+ color: #ebdbb2 !important;
81
+ }
82
+ .rule-section-head {
83
+ background-color: #32302f !important;
84
+ border-bottom-color: #504945 !important;
85
+ }
86
+ .rule-section-head h4, .rule-section-head p { color: #ebdbb2 !important; }
87
+
88
+ .form-control, .form-control:focus, .form-select,
89
+ select, textarea,
90
+ input[type=text], input[type=email], input[type=password],
91
+ input[type=number], input[type=search], input[type=url],
92
+ input[type=date], input[type=time], input[type=datetime-local] {
93
+ background-color: #32302f !important;
94
+ color: #ebdbb2 !important;
95
+ border-color: #504945 !important;
96
+ }
97
+ select option, .form-select option { background-color: #32302f; color: #ebdbb2; }
98
+ .form-control::placeholder { color: #a89984; }
99
+
100
+ .dropdown-menu {
101
+ background-color: #3c3836 !important;
102
+ border-color: #504945 !important;
103
+ color: #ebdbb2 !important;
104
+ }
105
+ .dropdown-item, .dropdown-menu > li > a {
106
+ color: #ebdbb2 !important;
107
+ }
108
+ .dropdown-item:hover, .dropdown-item:focus,
109
+ .dropdown-menu > li > a:hover, .dropdown-menu > li > a:focus {
110
+ background-color: #504945 !important;
111
+ color: #fabd2f !important;
112
+ }
113
+ .dropdown-divider, .dropdown-menu .divider { border-top-color: #504945 !important; background-color: #504945 !important; }
114
+ .dropdown-header { color: #a89984 !important; }
115
+
116
+ .btn-default, .btn-secondary, .btn-light,
117
+ .btn-outline-secondary, .btn-outline-default {
118
+ background-color: #504945 !important;
119
+ border-color: #665c54 !important;
120
+ color: #ebdbb2 !important;
121
+ }
122
+ .btn-default:hover, .btn-secondary:hover, .btn-light:hover,
123
+ .btn-outline-secondary:hover, .btn-outline-default:hover {
124
+ background-color: #665c54 !important;
125
+ color: #fabd2f !important;
126
+ }
127
+
128
+ .pagination .page-link {
129
+ background-color: #3c3836;
130
+ color: #ebdbb2;
131
+ border-color: #504945;
132
+ }
133
+ .pagination .page-item.active .page-link {
134
+ background-color: #d79921;
135
+ border-color: #d79921;
136
+ color: #282828;
137
+ }
138
+ .pagination .page-link:hover { background-color: #504945; color: #fabd2f; }
139
+
140
+ .modal-content { background-color: #3c3836 !important; color: #ebdbb2 !important; border-color: #504945 !important; }
141
+ .modal-header, .modal-footer { border-color: #504945 !important; }
142
+ .alert { background-color: #3c3836; color: #ebdbb2; border-color: #504945; }
143
+
144
+ .filters .filter-op, .filters select, .filters input { background-color: #32302f !important; color: #ebdbb2 !important; border-color: #504945 !important; }
145
+
146
+ .home-hero { color: #ebdbb2 !important; border-bottom-color: #504945 !important; }
147
+ .home-hero h1, .home-hero p { color: #ebdbb2 !important; }
148
+ .home-hero .build-pill { background-color: #d79921 !important; color: #282828 !important; }
149
+ .home-card {
150
+ background-color: #3c3836 !important;
151
+ border-color: #504945 !important;
152
+ color: #ebdbb2 !important;
153
+ box-shadow: 0 2px 6px rgba(0,0,0,0.45) !important;
154
+ }
155
+ .home-card h2, .home-card h4 { color: #ebdbb2 !important; border-bottom-color: #504945 !important; }
156
+ .links-list a { color: #ebdbb2 !important; }
157
+ .links-list a:hover { color: #fabd2f !important; }
158
+ #changelog-content {
159
+ background-color: #32302f !important;
160
+ border-color: #504945 !important;
161
+ color: #ebdbb2 !important;
162
+ }
163
+ #changelog-content details { border-left-color: #504945 !important; }
164
+ #changelog-content details[open] { border-left-color: #83a598 !important; }
165
+ #changelog-content summary.changelog-version::before { color: #a89984 !important; }
166
+ #changelog-content details[open] > summary.changelog-version::before { color: #83a598 !important; }
167
+ #changelog-content .changelog-version-title { color: #d5c4a1 !important; }
168
+ #changelog-content details[open] > summary .changelog-version-title { color: #ebdbb2 !important; }
169
+ .filter-chip { background-color: #32302f !important; border-color: #504945 !important; color: #ebdbb2 !important; }
170
+ .filter-chip.active-feat { color: #83a598 !important; border-color: #458588 !important; background-color: #1d2021 !important; }
171
+ .filter-chip.active-fix { color: #b8bb26 !important; border-color: #98971a !important; background-color: #1d2021 !important; }
172
+ .filter-chip.active-inc { color: #fb4934 !important; border-color: #cc241d !important; background-color: #1d2021 !important; }
173
+ .filter-chip.active-sec { color: #fe8019 !important; border-color: #d65d0e !important; background-color: #1d2021 !important; }
174
+ .filter-chip.active-oth { color: #a89984 !important; border-color: #504945 !important; background-color: #1d2021 !important; }
175
+ .filter-toggle-all { background-color: #504945 !important; color: #ebdbb2 !important; }
176
+ .filter-toggle-all:hover { background-color: #665c54 !important; }
177
+ .notice-box {
178
+ background-color: #3c3836 !important;
179
+ border-color: #d79921 !important;
180
+ border-left-color: #fabd2f !important;
181
+ color: #ebdbb2 !important;
182
+ }
183
+ .notice-box .notice-confirm { background-color: #d79921 !important; color: #282828 !important; }
184
+ .notice-box .notice-confirm:hover { background-color: #b57614 !important; }
185
+ .previous-releases a { background-color: #504945 !important; color: #ebdbb2 !important; }
186
+ .previous-releases a:hover { background-color: #665c54 !important; color: #fabd2f !important; }
187
+
188
+ /* Renderer-injected widgets: host_renderers.py emits inline <style>
189
+ blocks with hardcoded light-theme colours (e.g. .lbl-val:#2c3e50 on
190
+ white). Override the few classes whose colours don't read on dark
191
+ backgrounds. The badges themselves keep their contrast. */
192
+ .cmdb-label-row,
193
+ .cmdb-inv-grid .cmdb-label-row { border-bottom-color: #504945 !important; }
194
+ .cmdb-label-row .lbl-val,
195
+ .cmdb-inv-grid .lbl-val { color: #ebdbb2 !important; }
196
+ .cmdb-inv-grid .lbl-src { background: #504945 !important; color: #ebdbb2 !important; }
197
+ .cmdb-log-list { background: #32302f !important; border-color: #504945 !important; }
198
+ .cmdb-log-row { border-bottom-color: #504945 !important; }
199
+ .cmdb-log-row .log-msg { color: #ebdbb2 !important; }
200
+ .cmdb-log-row .log-ts,
201
+ .cmdb-log-meta { color: #a89984 !important; }
202
+
203
+ /* Nav-tabs strip at the top of every Flask-Admin edit/detail page
204
+ (List / Create / Edit / Details). Bootstrap defaults give the
205
+ active tab a white border-bottom and inactive tabs default link
206
+ blue, both invisible on dark themes. */
207
+ .nav-tabs {
208
+ border-bottom-color: #504945 !important;
209
+ }
210
+ .nav-tabs .nav-link {
211
+ color: #ebdbb2 !important;
212
+ border-color: transparent !important;
213
+ }
214
+ .nav-tabs .nav-link:hover,
215
+ .nav-tabs .nav-link:focus {
216
+ color: #fabd2f !important;
217
+ border-color: #504945 #504945 #504945 !important;
218
+ background-color: #3c3836 !important;
219
+ }
220
+ .nav-tabs .nav-link.active,
221
+ .nav-tabs .nav-item.show .nav-link {
222
+ background-color: #282828 !important;
223
+ color: #fabd2f !important;
224
+ border-color: #504945 #504945 #282828 !important;
225
+ }
226
+
227
+
228
+ /* Theme-aware surface tokens — used by debug_host, _host_tabs,
229
+ ansible_project_detail, host_relations_graph, ansible_rule_list,
230
+ ansible_playbook_run and any future template that opts in via
231
+ var(--surface-*, fallback). */
232
+ :root {
233
+ --surface-bg: #3c3836;
234
+ --surface-subtle: #504945;
235
+ --surface-border: #504945;
236
+ --surface-divider: #504945;
237
+ --surface-text: #ebdbb2;
238
+ --surface-muted: #a89984;
239
+ --debug-key: #8ec07c;
240
+ --debug-row-hit: #2d4a2d;
241
+ }