foreman_puppet 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (247) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +619 -0
  3. data/README.md +38 -0
  4. data/Rakefile +31 -0
  5. data/app/assets/stylesheets/foreman_puppet.scss +117 -0
  6. data/app/controllers/concerns/foreman_puppet/api/import_puppetclasses_common_controller.rb +139 -0
  7. data/app/controllers/concerns/foreman_puppet/environments_import.rb +61 -0
  8. data/app/controllers/concerns/foreman_puppet/extensions/api_hostgroups_controller.rb +40 -0
  9. data/app/controllers/concerns/foreman_puppet/extensions/api_template_combinations_controller.rb +23 -0
  10. data/app/controllers/concerns/foreman_puppet/extensions/api_v2_hosts_controller.rb +48 -0
  11. data/app/controllers/concerns/foreman_puppet/extensions/hostgroups_controller_extensions.rb +58 -0
  12. data/app/controllers/concerns/foreman_puppet/extensions/hosts_controller_extensions.rb +228 -0
  13. data/app/controllers/concerns/foreman_puppet/extensions/operatingsystems_controller.rb +11 -0
  14. data/app/controllers/concerns/foreman_puppet/extensions/parameters_host.rb +75 -0
  15. data/app/controllers/concerns/foreman_puppet/extensions/parameters_hostgroup.rb +70 -0
  16. data/app/controllers/concerns/foreman_puppet/extensions/parameters_template_combination.rb +21 -0
  17. data/app/controllers/concerns/foreman_puppet/parameters/config_group.rb +17 -0
  18. data/app/controllers/concerns/foreman_puppet/parameters/environment.rb +21 -0
  19. data/app/controllers/concerns/foreman_puppet/parameters/puppetclass.rb +24 -0
  20. data/app/controllers/concerns/foreman_puppet/parameters/puppetclass_lookup_key.rb +24 -0
  21. data/app/controllers/foreman_puppet/api/v2/base_controller.rb +26 -0
  22. data/app/controllers/foreman_puppet/api/v2/config_groups_controller.rb +57 -0
  23. data/app/controllers/foreman_puppet/api/v2/environments_controller.rb +91 -0
  24. data/app/controllers/foreman_puppet/api/v2/host_classes_controller.rb +59 -0
  25. data/app/controllers/foreman_puppet/api/v2/hostgroup_classes_controller.rb +46 -0
  26. data/app/controllers/foreman_puppet/api/v2/lookups_common_controller.rb +114 -0
  27. data/app/controllers/foreman_puppet/api/v2/override_values_controller.rb +99 -0
  28. data/app/controllers/foreman_puppet/api/v2/puppetclasses_controller.rb +99 -0
  29. data/app/controllers/foreman_puppet/api/v2/smart_class_parameters_controller.rb +76 -0
  30. data/app/controllers/foreman_puppet/config_groups_controller.rb +46 -0
  31. data/app/controllers/foreman_puppet/environments_controller.rb +51 -0
  32. data/app/controllers/foreman_puppet/puppet_smart_proxies_controller.rb +39 -0
  33. data/app/controllers/foreman_puppet/puppetclass_lookup_keys_controller.rb +33 -0
  34. data/app/controllers/foreman_puppet/puppetclasses_controller.rb +113 -0
  35. data/app/controllers/foreman_puppet/react_controller.rb +19 -0
  36. data/app/helpers/concerns/foreman_puppet/template_renderer_scope.rb +14 -0
  37. data/app/helpers/foreman_puppet/environments_helper.rb +17 -0
  38. data/app/helpers/foreman_puppet/hosts_and_hostgroups_helper.rb +96 -0
  39. data/app/helpers/foreman_puppet/hosts_helper.rb +32 -0
  40. data/app/helpers/foreman_puppet/puppet_smart_proxies_helper.rb +8 -0
  41. data/app/helpers/foreman_puppet/puppetclass_lookup_keys_helper.rb +135 -0
  42. data/app/helpers/foreman_puppet/puppetclasses_and_environments_helper.rb +55 -0
  43. data/app/helpers/foreman_puppet/puppetclasses_helper.rb +59 -0
  44. data/app/helpers/foreman_puppet/template_combinations_helper.rb +33 -0
  45. data/app/models/concerns/foreman_puppet/extensions/host.rb +88 -0
  46. data/app/models/concerns/foreman_puppet/extensions/hostgroup.rb +40 -0
  47. data/app/models/concerns/foreman_puppet/extensions/nic_managed.rb +11 -0
  48. data/app/models/concerns/foreman_puppet/extensions/operatingsystem.rb +11 -0
  49. data/app/models/concerns/foreman_puppet/extensions/provisioning_template.rb +64 -0
  50. data/app/models/concerns/foreman_puppet/extensions/report.rb +11 -0
  51. data/app/models/concerns/foreman_puppet/extensions/taxonomy.rb +19 -0
  52. data/app/models/concerns/foreman_puppet/extensions/template_combination.rb +23 -0
  53. data/app/models/concerns/foreman_puppet/extensions/user.rb +22 -0
  54. data/app/models/concerns/foreman_puppet/host_common.rb +90 -0
  55. data/app/models/concerns/foreman_puppet/puppet_lookup_value_extensions.rb +13 -0
  56. data/app/models/foreman_puppet/config_group.rb +45 -0
  57. data/app/models/foreman_puppet/config_group_class.rb +19 -0
  58. data/app/models/foreman_puppet/environment.rb +63 -0
  59. data/app/models/foreman_puppet/environment_class.rb +40 -0
  60. data/app/models/foreman_puppet/host_class.rb +23 -0
  61. data/app/models/foreman_puppet/host_config_group.rb +15 -0
  62. data/app/models/foreman_puppet/host_puppet_facet.rb +130 -0
  63. data/app/models/foreman_puppet/hostgroup_class.rb +23 -0
  64. data/app/models/foreman_puppet/hostgroup_puppet_facet.rb +98 -0
  65. data/app/models/foreman_puppet/puppetclass.rb +132 -0
  66. data/app/models/foreman_puppet/puppetclass_lookup_key.rb +58 -0
  67. data/app/services/foreman_puppet/host_info_providers/config_groups_info.rb +10 -0
  68. data/app/services/foreman_puppet/host_info_providers/puppet_info.rb +92 -0
  69. data/app/services/foreman_puppet/input_type/puppet_parameter_input.rb +35 -0
  70. data/app/services/foreman_puppet/proxy_status/puppet.rb +17 -0
  71. data/app/services/foreman_puppet/puppet_class_importer.rb +355 -0
  72. data/app/views/api/v2/template_combinations/base.json.erb +9 -0
  73. data/app/views/foreman_puppet/api/v2/config_groups/base.json.rabl +3 -0
  74. data/app/views/foreman_puppet/api/v2/config_groups/create.json.rabl +3 -0
  75. data/app/views/foreman_puppet/api/v2/config_groups/index.json.rabl +3 -0
  76. data/app/views/foreman_puppet/api/v2/config_groups/main.json.rabl +8 -0
  77. data/app/views/foreman_puppet/api/v2/config_groups/show.json.rabl +3 -0
  78. data/app/views/foreman_puppet/api/v2/config_groups/update.json.rabl +3 -0
  79. data/app/views/foreman_puppet/api/v2/environments/base.json.rabl +3 -0
  80. data/app/views/foreman_puppet/api/v2/environments/create.json.rabl +3 -0
  81. data/app/views/foreman_puppet/api/v2/environments/index.json.rabl +3 -0
  82. data/app/views/foreman_puppet/api/v2/environments/main.json.rabl +5 -0
  83. data/app/views/foreman_puppet/api/v2/environments/show.json.rabl +15 -0
  84. data/app/views/foreman_puppet/api/v2/environments/update.json.rabl +3 -0
  85. data/app/views/foreman_puppet/api/v2/host_puppet_facets/base.json.rabl +1 -0
  86. data/app/views/foreman_puppet/api/v2/host_puppet_facets/host_single.json.rabl +17 -0
  87. data/app/views/foreman_puppet/api/v2/host_puppet_facets/show.json.rabl +11 -0
  88. data/app/views/foreman_puppet/api/v2/hostgroup_puppet_facets/base.json.rabl +5 -0
  89. data/app/views/foreman_puppet/api/v2/hostgroup_puppet_facets/hostgroup_single.json.rabl +16 -0
  90. data/app/views/foreman_puppet/api/v2/hostgroup_puppet_facets/show.json.rabl +11 -0
  91. data/app/views/foreman_puppet/api/v2/import_puppetclasses/index.json.rabl +3 -0
  92. data/app/views/foreman_puppet/api/v2/import_puppetclasses/show.json.rabl +36 -0
  93. data/app/views/foreman_puppet/api/v2/override_values/create.json.rabl +3 -0
  94. data/app/views/foreman_puppet/api/v2/override_values/index.json.rabl +3 -0
  95. data/app/views/foreman_puppet/api/v2/override_values/show.json.rabl +3 -0
  96. data/app/views/foreman_puppet/api/v2/override_values/update.json.rabl +3 -0
  97. data/app/views/foreman_puppet/api/v2/puppetclasses/base.json.rabl +3 -0
  98. data/app/views/foreman_puppet/api/v2/puppetclasses/create.json.rabl +3 -0
  99. data/app/views/foreman_puppet/api/v2/puppetclasses/index.json.rabl +4 -0
  100. data/app/views/foreman_puppet/api/v2/puppetclasses/list.json.rabl +3 -0
  101. data/app/views/foreman_puppet/api/v2/puppetclasses/main.json.rabl +5 -0
  102. data/app/views/foreman_puppet/api/v2/puppetclasses/show.json.rabl +15 -0
  103. data/app/views/foreman_puppet/api/v2/puppetclasses/update.json.rabl +3 -0
  104. data/app/views/foreman_puppet/api/v2/smart_class_parameters/base.json.rabl +4 -0
  105. data/app/views/foreman_puppet/api/v2/smart_class_parameters/create.json.rabl +3 -0
  106. data/app/views/foreman_puppet/api/v2/smart_class_parameters/destroy.json.rabl +3 -0
  107. data/app/views/foreman_puppet/api/v2/smart_class_parameters/index.json.rabl +3 -0
  108. data/app/views/foreman_puppet/api/v2/smart_class_parameters/main.json.rabl +23 -0
  109. data/app/views/foreman_puppet/api/v2/smart_class_parameters/show.json.rabl +19 -0
  110. data/app/views/foreman_puppet/api/v2/smart_class_parameters/update.json.rabl +3 -0
  111. data/app/views/foreman_puppet/config_groups/_config_group.html.erb +34 -0
  112. data/app/views/foreman_puppet/config_groups/_config_groups_selection.html.erb +36 -0
  113. data/app/views/foreman_puppet/config_groups/_form.html.erb +9 -0
  114. data/app/views/foreman_puppet/config_groups/edit.html.erb +3 -0
  115. data/app/views/foreman_puppet/config_groups/index.html.erb +31 -0
  116. data/app/views/foreman_puppet/config_groups/new.html.erb +3 -0
  117. data/app/views/foreman_puppet/config_groups/welcome.html.erb +12 -0
  118. data/app/views/foreman_puppet/environments/_form.html.erb +20 -0
  119. data/app/views/foreman_puppet/environments/edit.html.erb +8 -0
  120. data/app/views/foreman_puppet/environments/index.html.erb +32 -0
  121. data/app/views/foreman_puppet/environments/new.html.erb +7 -0
  122. data/app/views/foreman_puppet/environments/welcome.html.erb +16 -0
  123. data/app/views/foreman_puppet/layouts/application_react.html.erb +15 -0
  124. data/app/views/foreman_puppet/puppet_smart_proxies/_dashboard.html.erb +9 -0
  125. data/app/views/foreman_puppet/puppet_smart_proxies/_environments.html.erb +30 -0
  126. data/app/views/foreman_puppet/puppetclass_lookup_keys/edit.html.erb +3 -0
  127. data/app/views/foreman_puppet/puppetclass_lookup_keys/index.html.erb +22 -0
  128. data/app/views/foreman_puppet/puppetclass_lookup_keys/welcome.html.erb +9 -0
  129. data/app/views/foreman_puppet/puppetclasses/_class_parameters.html.erb +37 -0
  130. data/app/views/foreman_puppet/puppetclasses/_class_selection.html.erb +70 -0
  131. data/app/views/foreman_puppet/puppetclasses/_classes.html.erb +22 -0
  132. data/app/views/foreman_puppet/puppetclasses/_classes_in_groups.html.erb +5 -0
  133. data/app/views/foreman_puppet/puppetclasses/_classes_parameters.html.erb +16 -0
  134. data/app/views/foreman_puppet/puppetclasses/_form.html.erb +62 -0
  135. data/app/views/foreman_puppet/puppetclasses/_selected_classes.html.erb +4 -0
  136. data/app/views/foreman_puppet/puppetclasses/edit.html.erb +4 -0
  137. data/app/views/foreman_puppet/puppetclasses/index.html.erb +47 -0
  138. data/app/views/hosts/_form_puppet_enc_tab.html.erb +24 -0
  139. data/app/views/hosts/foreman_puppet/_form_main_tab_fields.html.erb +1 -0
  140. data/app/views/hosts/select_multiple_environment.html.erb +8 -0
  141. data/app/views/provisioning_templates/_combination.html.erb +5 -0
  142. data/app/views/provisioning_templates/_combinations.html.erb +6 -0
  143. data/app/views/smart_proxies/plugins/_puppet.html.erb +24 -0
  144. data/config/api_routes.rb +81 -0
  145. data/config/routes.rb +89 -0
  146. data/db/migrate/20101121140000_add_environment_to_template_combinations.foreman_puppet.rb +9 -0
  147. data/db/migrate/20200720123005_migrate_puppet_core_types.foreman_puppet.rb +19 -0
  148. data/db/migrate/20200722171017_create_host_puppet_facet.foreman_puppet.rb +10 -0
  149. data/db/migrate/20200803113531_create_hostgroup_puppet_facet.foreman_puppet.rb +10 -0
  150. data/db/migrate/20200803113803_migrate_environment_to_puppet_facet.foreman_puppet.rb +22 -0
  151. data/db/migrate/20200803113903_migrate_host_type_in_host_config_groups.foreman_puppet.rb +29 -0
  152. data/db/migrate/20201125113903_migrate_puppetclasses_to_facets.foreman_puppet.rb +47 -0
  153. data/db/migrate_foreman/20090722141107_create_environments.rb +17 -0
  154. data/db/migrate_foreman/20120905095532_create_environment_classes.rb +15 -0
  155. data/db/migrate_foreman/20140407161817_create_config_groups.rb +9 -0
  156. data/db/migrate_foreman/20140407162007_create_config_group_classes.rb +10 -0
  157. data/db/migrate_foreman/20140407162059_create_host_config_groups.rb +11 -0
  158. data/db/migrate_foreman/20161205142618_delete_orphaned_smart_class_parameters.rb +10 -0
  159. data/db/migrate_foreman/20170109115157_fix_lookup_key_auditable_type.rb +15 -0
  160. data/db/migrate_foreman/20180816134832_cast_lookup_key_values.rb +35 -0
  161. data/db/migrate_foreman/20181023112532_add_environment_puppetclass_id.rb +7 -0
  162. data/db/migrate_foreman/20181224174419_add_index_to_environment_class_by_lookup_key_and_puppetclass.rb +6 -0
  163. data/db/seeds.d/111_puppet_proxy_feature.rb +8 -0
  164. data/lib/foreman_puppet.rb +10 -0
  165. data/lib/foreman_puppet/engine.rb +82 -0
  166. data/lib/foreman_puppet/register.rb +218 -0
  167. data/lib/foreman_puppet/version.rb +3 -0
  168. data/lib/tasks/foreman_puppet_tasks.rake +31 -0
  169. data/locale/Makefile +60 -0
  170. data/locale/action_names.rb +5 -0
  171. data/locale/en/foreman_puppet.edit.po +911 -0
  172. data/locale/en/foreman_puppet.po +690 -0
  173. data/locale/en/foreman_puppet.po.time_stamp +0 -0
  174. data/locale/foreman_puppet.pot +1076 -0
  175. data/locale/gemspec.rb +2 -0
  176. data/test/controllers/foreman_puppet/api/v2/config_groups_controller_test.rb +28 -0
  177. data/test/controllers/foreman_puppet/api/v2/environments_controller_test.rb +346 -0
  178. data/test/controllers/foreman_puppet/api/v2/host_classes_controller_test.rb +48 -0
  179. data/test/controllers/foreman_puppet/api/v2/hostgroup_classes_controller_test.rb +41 -0
  180. data/test/controllers/foreman_puppet/api/v2/hostgroups_controller_test.rb +79 -0
  181. data/test/controllers/foreman_puppet/api/v2/hosts_controller_test.rb +101 -0
  182. data/test/controllers/foreman_puppet/api/v2/lookups_common_controller_test.rb +29 -0
  183. data/test/controllers/foreman_puppet/api/v2/override_values_controller_test.rb +169 -0
  184. data/test/controllers/foreman_puppet/api/v2/puppetclasses_controller_test.rb +144 -0
  185. data/test/controllers/foreman_puppet/api/v2/smart_class_parameters_controller_test.rb +557 -0
  186. data/test/controllers/foreman_puppet/api/v2/template_combinations_controller_test.rb +81 -0
  187. data/test/controllers/foreman_puppet/config_groups_controller_test.rb +47 -0
  188. data/test/controllers/foreman_puppet/environments_controller_test.rb +230 -0
  189. data/test/controllers/foreman_puppet/hostgroups_controller_test.rb +72 -0
  190. data/test/controllers/foreman_puppet/hosts_controller_test.rb +346 -0
  191. data/test/controllers/foreman_puppet/puppet_smart_proxies_controller_test.rb +29 -0
  192. data/test/controllers/foreman_puppet/puppetclass_lookup_keys_controller_test.rb +59 -0
  193. data/test/controllers/foreman_puppet/puppetclasses_controller_test.rb +235 -0
  194. data/test/controllers/provisioning_templates_controller_test.rb +70 -0
  195. data/test/factories/foreman_puppet_factories.rb +134 -0
  196. data/test/factories/host_puppet_enhancements.rb +61 -0
  197. data/test/factories/proxy_puppet_enhancements.rb +33 -0
  198. data/test/helpers/foreman_puppet/hosts_and_hostgroups_helper_test.rb +65 -0
  199. data/test/helpers/foreman_puppet/puppetclasses_helper_test.rb +33 -0
  200. data/test/integration/foreman_puppet/environment_js_test.rb +27 -0
  201. data/test/integration/foreman_puppet/host_js_test.rb +371 -0
  202. data/test/integration/foreman_puppet/hostgroup_js_test.rb +100 -0
  203. data/test/integration/foreman_puppet/puppetclass_js_test.rb +37 -0
  204. data/test/integration/foreman_puppet/smartclass_parameter_js_test.rb +84 -0
  205. data/test/models/foreman_puppet/config_group_class_test.rb +9 -0
  206. data/test/models/foreman_puppet/config_group_test.rb +8 -0
  207. data/test/models/foreman_puppet/environment_test.rb +92 -0
  208. data/test/models/foreman_puppet/host_config_group_test.rb +39 -0
  209. data/test/models/foreman_puppet/host_puppet_facet_test.rb +116 -0
  210. data/test/models/foreman_puppet/host_test.rb +288 -0
  211. data/test/models/foreman_puppet/hostgroup_puppet_facet_test.rb +200 -0
  212. data/test/models/foreman_puppet/hostgroup_test.rb +14 -0
  213. data/test/models/foreman_puppet/lookup_value_test.rb +69 -0
  214. data/test/models/foreman_puppet/provisioning_template_test.rb +124 -0
  215. data/test/models/foreman_puppet/puppetclass_lookup_key_test.rb +81 -0
  216. data/test/models/foreman_puppet/puppetclass_test.rb +144 -0
  217. data/test/models/foreman_puppet/smart_proxy_test.rb +28 -0
  218. data/test/qraphql/queries/host_puppet_query_test.rb +36 -0
  219. data/test/qraphql/queries/hostgroup_puppet_query_test.rb +36 -0
  220. data/test/services/foreman_puppet/host_info_providers/puppet_info_test.rb +791 -0
  221. data/test/services/foreman_puppet/input_type/puppet_parameter_input_test.rb +14 -0
  222. data/test/test_puppet_helper.rb +30 -0
  223. data/test/unit/foreman_puppet/access_permissions_test.rb +16 -0
  224. data/test/unit/foreman_puppet/puppet_class_importer_test.rb +247 -0
  225. data/test/unit/foreman_puppet/template_rendering_test.rb +20 -0
  226. data/test/unit/foreman_puppet_test.rb +11 -0
  227. data/webpack/__mocks__/foremanReact/common/I18n.js +7 -0
  228. data/webpack/__mocks__/foremanReact/components/Layout/LayoutActions.js +2 -0
  229. data/webpack/__mocks__/foremanReact/readme.md +11 -0
  230. data/webpack/__mocks__/foremanReact/redux/API/APISelectors.js +10 -0
  231. data/webpack/__mocks__/foremanReact/redux/API/index.js +10 -0
  232. data/webpack/__mocks__/foremanReact/redux/actions/toasts.js +8 -0
  233. data/webpack/__mocks__/foremanReact/redux/index.js +1 -0
  234. data/webpack/__mocks__/foremanReact/redux/middlewares/IntervalMiddleware.js +5 -0
  235. data/webpack/fills_index.js +30 -0
  236. data/webpack/index.js +18 -0
  237. data/webpack/src/ForemanPuppet.js +11 -0
  238. data/webpack/src/Router/__snapshots__/routes.test.js.snap +3 -0
  239. data/webpack/src/Router/index.js +14 -0
  240. data/webpack/src/Router/routes.js +3 -0
  241. data/webpack/src/Router/routes.test.js +16 -0
  242. data/webpack/src/foreman_class_edit.js +224 -0
  243. data/webpack/src/foreman_puppet_host_form.js +140 -0
  244. data/webpack/src/foreman_puppet_host_form.test.js +65 -0
  245. data/webpack/src/index.js +1 -0
  246. data/webpack/src/reducers.js +7 -0
  247. metadata +340 -0
@@ -0,0 +1,81 @@
1
+ require 'test_puppet_helper'
2
+
3
+ module ForemanPuppet
4
+ module Api
5
+ module V2
6
+ class TemplateCombinationsControllerTest < ActionController::TestCase
7
+ tests ::Api::V2::TemplateCombinationsController
8
+
9
+ let(:environment) { FactoryBot.create(:environment) }
10
+ let(:template_combination) { FactoryBot.create(:template_combination) }
11
+
12
+ test 'should get index by environment' do
13
+ FactoryBot.create(:template_combination, environment: template_combination.environment)
14
+ get :index, params: { environment_id: template_combination.environment.to_param }
15
+ json_response = ActiveSupport::JSON.decode(@response.body)
16
+ assert_equal 2, json_response['results'].size, 'Should contain template_combinations in the response'
17
+ assert_response :success
18
+ end
19
+
20
+ context 'with provisioning_template_id' do
21
+ setup do
22
+ Foreman::Deprecation.stubs(:api_deprecation_warning).never
23
+ end
24
+
25
+ test 'should get index' do
26
+ FactoryBot.create(:template_combination, provisioning_template: template_combination.provisioning_template)
27
+ get :index, params: { provisioning_template_id: template_combination.provisioning_template.id }
28
+ json_response = ActiveSupport::JSON.decode(@response.body)
29
+ assert_equal 2, json_response['results'].size, 'Should contain template_combinations in the response'
30
+ assert_response :success
31
+ end
32
+
33
+ test 'should get template combination for template' do
34
+ get :show, params: { provisioning_template_id: template_combination.provisioning_template.to_param, id: template_combination.id }
35
+ assert_response :success
36
+ json_response = ActiveSupport::JSON.decode(@response.body)
37
+ assert_not json_response.empty?
38
+ assert_equal json_response['provisioning_template_id'], template_combination.provisioning_template_id
39
+ end
40
+
41
+ test 'should get template combination for environment' do
42
+ get :show, params: { provisioning_template_id: template_combination.provisioning_template.to_param, id: template_combination.id }
43
+ assert_response :success
44
+ json_response = ActiveSupport::JSON.decode(@response.body)
45
+ assert_not json_response.empty?
46
+ assert_equal json_response['environment_id'], template_combination.environment_id
47
+ assert_equal json_response['environment_name'], template_combination.environment.name
48
+ end
49
+
50
+ test 'should create valid' do
51
+ as_admin do
52
+ post :create, params: { template_combination: { environment_id: environment.id, hostgroup_id: hostgroups(:unusual).id },
53
+ provisioning_template_id: template_combination.provisioning_template.id }
54
+ end
55
+ json_response = ActiveSupport::JSON.decode(@response.body)
56
+ assert_equal(json_response['environment_id'], environment.id)
57
+ assert_equal(json_response['hostgroup_id'], hostgroups(:unusual).id)
58
+ assert_equal(json_response['provisioning_template_id'], template_combination.provisioning_template.id)
59
+ assert_response :created
60
+ end
61
+
62
+ test 'should update template combination' do
63
+ put :update, params: { template_combination: { environment_id: environment.id, hostgroup_id: hostgroups(:common).id },
64
+ environment_id: template_combination.environment.id, id: template_combination.id }
65
+
66
+ json_response = ActiveSupport::JSON.decode(@response.body)
67
+ assert_equal(json_response['environment_id'], environment.id)
68
+ assert_equal(json_response['hostgroup_id'], hostgroups(:common).id)
69
+ assert_response :success
70
+ end
71
+
72
+ test 'should destroy' do
73
+ delete :destroy, params: { id: template_combination.id }
74
+ assert_response :ok
75
+ assert_not TemplateCombination.exists?(template_combination.id)
76
+ end
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
@@ -0,0 +1,47 @@
1
+ require 'test_puppet_helper'
2
+
3
+ module ForemanPuppet
4
+ class ConfigGroupsControllerTest < ActionController::TestCase
5
+ setup do
6
+ @routes = ForemanPuppet::Engine.routes
7
+ end
8
+
9
+ basic_pagination_per_page_test
10
+ basic_pagination_rendered_test
11
+
12
+ test 'should get index' do
13
+ get :index, session: set_session_user
14
+ assert_response :success
15
+ assert_not_empty assigns(:config_groups)
16
+ end
17
+
18
+ test 'should get new' do
19
+ get :new, session: set_session_user
20
+ assert_response :success
21
+ end
22
+
23
+ test 'should create config_group' do
24
+ assert_difference('ForemanPuppet::ConfigGroup.count') do
25
+ post :create, params: { config_group: { name: 'Custom Dev Group' } }, session: set_session_user
26
+ end
27
+ assert_redirected_to config_groups_path
28
+ end
29
+
30
+ test 'should get edit' do
31
+ get :edit, params: { id: config_groups(:one) }, session: set_session_user
32
+ assert_response :success
33
+ end
34
+
35
+ test 'should update config_group' do
36
+ put :update, params: { id: config_groups(:one), config_group: { name: 'new name' } }, session: set_session_user
37
+ assert_redirected_to config_groups_path
38
+ end
39
+
40
+ test 'should destroy config_group' do
41
+ assert_difference('ForemanPuppet::ConfigGroup.count', -1) do
42
+ delete :destroy, params: { id: config_groups(:three) }, session: set_session_user
43
+ end
44
+ assert_redirected_to config_groups_path
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,230 @@
1
+ require 'test_puppet_helper'
2
+
3
+ module ForemanPuppet
4
+ class EnvironmentsControllerTest < ActionController::TestCase
5
+ setup do
6
+ @routes = ForemanPuppet::Engine.routes
7
+ @model = FactoryBot.create(:environment)
8
+ end
9
+
10
+ basic_index_test(:environments)
11
+ basic_new_test
12
+ basic_edit_test(:environment)
13
+ basic_pagination_per_page_test
14
+ basic_pagination_rendered_test
15
+
16
+ test 'should create new environment' do
17
+ assert_difference -> { ForemanPuppet::Environment.unscoped.count } do
18
+ post :create, params: { commit: 'Create', environment: { name: 'some_environment' } }, session: set_session_user
19
+ end
20
+ assert_redirected_to environments_path
21
+ end
22
+
23
+ test 'should update environment' do
24
+ setup_users
25
+ environment = Environment.new name: 'some_environment'
26
+ assert environment.save!
27
+
28
+ put :update, params: { commit: 'Update', id: environment.name, environment: { name: 'other_environment' } }, session: set_session_user
29
+ env = Environment.unscoped.find(environment.id)
30
+ assert_equal('other_environment', env.name)
31
+
32
+ assert_redirected_to environments_path
33
+ end
34
+
35
+ test 'should destroy environment' do
36
+ setup_users
37
+ environment = Environment.new name: 'some_environment'
38
+ assert environment.save!
39
+
40
+ assert_difference('Environment.unscoped.count', -1) do
41
+ delete :destroy, params: { id: environment.name }, session: set_session_user
42
+ end
43
+
44
+ assert_redirected_to environments_path
45
+ end
46
+
47
+ describe 'environments import' do
48
+ let(:puppet_proxy) { FactoryBot.create(:puppet_smart_proxy) }
49
+
50
+ test 'should import as admin when organization changed' do
51
+ setup_import_classes
52
+ Organization.current = taxonomies(:organization2)
53
+ post :obsolete_and_new, params:
54
+ { 'changed' =>
55
+ { 'new' =>
56
+ { 'env1' => '{"a":{"new":{}}}' } } }, session: set_session_user
57
+ assert_redirected_to environments_url
58
+ end
59
+
60
+ test 'should handle disk environment containing additional classes' do
61
+ setup_import_classes
62
+ Environment.find_by(name: 'env1').puppetclasses.delete(Puppetclass.find_by(name: 'a'))
63
+ # db_tree of {"env1" => ["b", "c"], "env2" => ["a", "b", "c"]}
64
+ # disk_tree of {"env1" => ["a", "b", "c"],"env2" => ["a", "b", "c"]}
65
+ get :import_environments, params: { proxy: puppet_proxy }, session: set_session_user
66
+ assert_template 'common/_puppetclasses_or_envs_changed'
67
+ assert_select 'input#changed_new_env1'
68
+ post :obsolete_and_new, params:
69
+ { 'changed' =>
70
+ { 'new' =>
71
+ { 'env1' => '{"a":{"new":{}}}' } } }, session: set_session_user
72
+ assert_redirected_to environments_url
73
+ assert_equal 'Successfully updated environments and Puppet classes from the on-disk Puppet installation', flash[:success]
74
+ assert_equal %w[a b c],
75
+ Environment.unscoped.find_by(name: 'env1').puppetclasses.map(&:name).sort
76
+ end
77
+
78
+ test 'should handle disk environment containing less classes' do
79
+ setup_import_classes
80
+ as_admin { Puppetclass.create(name: 'd') }
81
+ Environment.find_by(name: 'env1').puppetclasses << Puppetclass.find_by(name: 'd')
82
+ # db_tree of {"env1" => ["a", "b", "c", "d"], "env2" => ["a", "b", "c"]}
83
+ # disk_tree of {"env1" => ["a", "b", "c"], "env2" => ["a", "b", "c"]}
84
+ get :import_environments, params: { proxy: puppet_proxy }, session: set_session_user
85
+ assert_template 'common/_puppetclasses_or_envs_changed'
86
+ assert_select 'input#changed_obsolete_env1[value*="d"]'
87
+ post :obsolete_and_new,
88
+ params: { 'changed' =>
89
+ { 'obsolete' =>
90
+ { 'env1' => '["d"]' } } }, session: set_session_user
91
+ assert_redirected_to environments_url
92
+ assert_equal 'Successfully updated environments and Puppet classes from the on-disk Puppet installation', flash[:success]
93
+ envs = Environment.unscoped.find_by(name: 'env1').puppetclasses.map(&:name).sort
94
+ assert_equal %w[a b c], envs
95
+ end
96
+ test 'should handle disk environment containing less environments' do
97
+ setup_import_classes
98
+ as_admin { Environment.create(name: 'env3') }
99
+ # db_tree of {"env1" => ["a", "b", "c"], "env2" => ["a", "b", "c"], "env3" => []}
100
+ # disk_tree of {"env1" => ["a", "b", "c"], "env2" => ["a", "b", "c"]}
101
+ get :import_environments, params: { proxy: puppet_proxy.id }, session: set_session_user
102
+ assert_template 'common/_puppetclasses_or_envs_changed'
103
+ assert_select 'input#changed_obsolete_env3'
104
+ post :obsolete_and_new, params:
105
+ { 'changed' =>
106
+ { 'obsolete' =>
107
+ { 'env3' => '[]' } } }, session: set_session_user
108
+ assert_redirected_to environments_url
109
+ assert_equal 'Successfully updated environments and Puppet classes from the on-disk Puppet installation', flash[:success]
110
+ assert_equal [], Environment.unscoped.find_by(name: 'env3').puppetclasses.map(&:name).sort
111
+ end
112
+
113
+ test 'should fail to remove active environments' do
114
+ disable_orchestration
115
+ setup_import_classes
116
+ as_admin do
117
+ host = FactoryBot.create(:host)
118
+ Environment.find_by(name: 'env1').puppetclasses += [FactoryBot.create(:puppetclass)]
119
+ host.attributes = { puppet_attributes: { environment_id: Environment.find_by(name: 'env1').id } }
120
+ assert host.save!
121
+ assert_empty host.errors
122
+ assert Environment.find_by(name: 'env1').hosts.count.positive?
123
+ end
124
+
125
+ # assert_template "puppetclasses_or_envs_changed". This assertion will fail. And it should fail. See above.
126
+ post :obsolete_and_new, params:
127
+ { 'changed' =>
128
+ { 'obsolete' =>
129
+ { 'env1' => '["a","b","c","_destroy_"]' } } }, session: set_session_user
130
+ assert Environment.unscoped.find_by(name: 'env1').hosts.count.positive?
131
+ # assert flash[:error] =~ /^Failed to update the environments and puppetclasses from the on-disk puppet installation/
132
+ assert Environment.unscoped.find_by(name: 'env1')
133
+ end
134
+
135
+ test 'should obey config/ignored_environments.yml' do
136
+ @request.env['HTTP_REFERER'] = environments_url
137
+ setup_import_classes
138
+ as_admin do
139
+ Environment.create name: 'env3'
140
+ Environment.find_by(name: 'env2').destroy
141
+ end
142
+ # db_tree of {"env1" => ["a", "b", "c"], "env3" => []}
143
+ # disk_tree of {"env1" => ["a", "b", "c"], "env2" => ["a", "b", "c"]}
144
+
145
+ PuppetClassImporter.any_instance.stubs(:ignored_environments).returns(%w[env1 env2 env3])
146
+ get :import_environments, params: { proxy: puppet_proxy }, session: set_session_user
147
+
148
+ assert_equal "No changes to your environments detected\nIgnored environments: env1, env2, and env3", flash[:info]
149
+ end
150
+
151
+ test 'should obey puppet class filters in config/ignored_environments.yml' do
152
+ setup_import_classes
153
+ PuppetClassImporter.any_instance.stubs(:updated_classes_for).returns([])
154
+ PuppetClassImporter.any_instance.stubs(:removed_classes_for).returns([])
155
+
156
+ PuppetClassImporter.any_instance.stubs(:ignored_environments).returns([])
157
+ PuppetClassImporter.any_instance.stubs(:ignored_classes).returns([/^a$/])
158
+ get :import_environments, params: { proxy: puppet_proxy }, session: set_session_user
159
+
160
+ assert_equal "No changes to your environments detected\nIgnored classes in the environments: env1 and env2", flash[:info]
161
+ end
162
+
163
+ test 'it adds a warning when boolean keys are found' do
164
+ setup_import_classes
165
+ PuppetClassImporter.any_instance.stubs(:ignored_environments).returns([true])
166
+
167
+ get :import_environments, params: { proxy: puppet_proxy }, session: set_session_user
168
+ assert_equal 'Ignored environment names resulting in booleans found. Please quote strings like true/false and yes/no in config/ignored_environments.yml', flash[:warning]
169
+ end
170
+
171
+ test 'user with viewer rights should fail to edit an environment' do
172
+ setup_user
173
+ get :edit, params: { id: environments(:production).name }, session: set_session_user.merge(user: users(:one).id)
174
+ assert_equal(403, @response.status)
175
+ end
176
+
177
+ test 'user with viewer rights should succeed in viewing environments' do
178
+ setup_user
179
+ get :index, session: set_session_user
180
+ assert_response :success
181
+ end
182
+
183
+ test "should accept environment with name 'name'" do
184
+ @request.env['HTTP_REFERER'] = environments_url
185
+ ProxyAPI::Puppet.any_instance.stubs(:environments).returns(['new'])
186
+ post :obsolete_and_new, params:
187
+ { 'changed' =>
188
+ { 'new' =>
189
+ { 'new' => '{"a":{"new":{}}}' } } }, session: set_session_user
190
+ assert_includes(Environment.unscoped.all.map(&:name), 'new', 'Should include environment with name "new"')
191
+ end
192
+
193
+ private
194
+
195
+ def setup_import_classes
196
+ as_admin do
197
+ Host::Managed.all.each { |h| h.update(environment_id: nil) }
198
+ Hostgroup.all.each { |h| h.update(environment_id: nil) }
199
+ Puppetclass.destroy_all
200
+ Environment.destroy_all
201
+ end
202
+ @request.env['HTTP_REFERER'] = environments_url
203
+ # This is the database status
204
+ # and should result in a db_tree of {"env1" => ["a", "b", "c"], "env2" => ["a", "b", "c"]}
205
+ orgs = [taxonomies(:organization1)]
206
+ locs = [taxonomies(:location1)]
207
+ as_admin do
208
+ klasses = %w[a b c].map { |name| FactoryBot.create :puppetclass, name: name }
209
+ %w[env1 env2].each do |name|
210
+ env = FactoryBot.create :environment, name: name, organizations: orgs, locations: locs
211
+ env.puppetclasses += klasses
212
+ end
213
+ end
214
+ # This is the on-disk status
215
+ # and should result in a disk_tree of {"env1" => ["a", "b", "c"],"env2" => ["a", "b", "c"]}
216
+ envs = HashWithIndifferentAccess.new(env1: %w[a b c], env2: %w[a b c])
217
+ pcs = [HashWithIndifferentAccess.new('a' => { 'name' => 'a', 'module' => '', 'params' => {} })]
218
+ classes = Hash[pcs.map { |k| [k.keys.first, Foreman::ImporterPuppetclass.new(k.values.first)] }]
219
+ Environment.expects(:puppetEnvs).returns(envs).at_least(0)
220
+ ProxyAPI::Puppet.any_instance.stubs(:environments).returns(%w[env1 env2])
221
+ ProxyAPI::Puppet.any_instance.stubs(:classes).returns(classes)
222
+ end
223
+ end
224
+
225
+ def setup_user
226
+ @request.session[:user] = users(:one).id
227
+ users(:one).roles = [Role.default, Role.find_by(name: 'Viewer')]
228
+ end
229
+ end
230
+ end
@@ -0,0 +1,72 @@
1
+ require 'test_puppet_helper'
2
+
3
+ module ForemanPuppet
4
+ class HostgroupsControllerTest < ActionController::TestCase
5
+ tests ::HostgroupsController
6
+
7
+ setup do
8
+ @routes = ForemanPuppet::Engine.routes
9
+ end
10
+
11
+ describe '#environment_selected' do
12
+ setup do
13
+ @environment = FactoryBot.create(:environment)
14
+ @puppetclass = FactoryBot.create(:puppetclass)
15
+ @hostgroup = FactoryBot.create(:hostgroup, :with_puppet_enc, environment: @environment)
16
+ @params = {
17
+ id: @hostgroup.id,
18
+ hostgroup: {
19
+ name: @hostgroup.name,
20
+ environment_id: '',
21
+ puppetclass_ids: [@puppetclass.id],
22
+ },
23
+ }
24
+ end
25
+
26
+ test 'should return the selected puppet classes on environment change' do
27
+ assert_equal 0, @hostgroup.puppet.puppetclasses.length
28
+
29
+ post :environment_selected, params: @params, session: set_session_user, xhr: true
30
+ assert_equal(1, assigns(:hostgroup).puppet.puppetclasses.length)
31
+ assert_include assigns(:hostgroup).puppet.puppetclasses, @puppetclass
32
+ end
33
+
34
+ context 'environment_id param is set' do
35
+ test 'it will take the hostgroup params environment_id' do
36
+ other_environment = FactoryBot.create(:environment)
37
+ @params[:hostgroup][:environment_id] = other_environment.id
38
+
39
+ post :environment_selected, params: @params, session: set_session_user, xhr: true
40
+ assert_equal assigns(:environment), other_environment
41
+ end
42
+ end
43
+
44
+ test 'should not escape lookup values on environment change' do
45
+ hostgroup = FactoryBot.create(:hostgroup, :with_puppet_enc, environment: @environment, puppetclasses: [@puppetclass])
46
+ lookup_key = FactoryBot.create(:puppetclass_lookup_key, :array, default_value: %w[a b],
47
+ override: true,
48
+ puppetclass: @puppetclass,
49
+ overrides: { "hostgroup=#{hostgroup.name}" => %w[c d] })
50
+ lookup_value = lookup_key.lookup_values.first
51
+ FactoryBot.create(:environment_class, puppetclass: @puppetclass, environment: @environment, puppetclass_lookup_key: lookup_key)
52
+
53
+ # sending exactly what the host form would send which is lookup_value.value_before_type_cast
54
+ lk = { 'lookup_values_attributes' => { lookup_key.id.to_s => { 'value' => lookup_value.value_before_type_cast,
55
+ 'id' => lookup_value.id,
56
+ 'lookup_key_id' => lookup_key.id,
57
+ '_destroy' => false } } }
58
+
59
+ params = {
60
+ hostgroup_id: hostgroup.id,
61
+ hostgroup: hostgroup.attributes.merge(lk),
62
+ }
63
+
64
+ # environment change calls puppetclass_parameters which caused the extra escaping
65
+ post :puppetclass_parameters, params: params, session: set_session_user, xhr: true
66
+
67
+ # if this was escaped during refresh_host the value in response.body after unescapeHTML would include "[\\\"c\\\",\\\"d\\\"]"
68
+ assert_includes CGI.unescapeHTML(response.body), '["c","d"]'
69
+ end
70
+ end
71
+ end
72
+ end
@@ -0,0 +1,346 @@
1
+ require 'test_puppet_helper'
2
+
3
+ module ForemanPuppet
4
+ class HostsControllerTest < ActionController::TestCase
5
+ tests ::HostsController
6
+
7
+ setup do
8
+ @routes = ForemanPuppet::Engine.routes
9
+ as_admin do
10
+ host1
11
+ host2
12
+ end
13
+ end
14
+
15
+ let(:org) { users(:one).organizations.first }
16
+ let(:loc) { users(:one).locations.first }
17
+ let(:environment1) { FactoryBot.create(:environment, organizations: [org], locations: [loc]) }
18
+ let(:environment2) { FactoryBot.create(:environment, organizations: [org], locations: [loc]) }
19
+ let(:hostgroup) { FactoryBot.create(:hostgroup, :with_puppet_enc, environment: environment2, organizations: [org], locations: [loc]) }
20
+ let(:host_defaults) { { hostgroup: hostgroup, environment: environment1, organization: org, location: loc } }
21
+ let(:host1) { FactoryBot.create(:host, :with_puppet_enc, :with_puppetclass, host_defaults) }
22
+ let(:host2) { FactoryBot.create(:host, :with_puppet_enc, :with_puppetclass, host_defaults) }
23
+
24
+ test 'user with edit host rights with update environments should change environments' do
25
+ @request.env['HTTP_REFERER'] = '/hosts'
26
+ setup_user 'edit', 'hosts'
27
+
28
+ post :update_multiple_environment, params: { host_ids: [host1.id, host2.id],
29
+ environment: { id: environment2.id } },
30
+ session: set_session_user(:one)
31
+ assert_equal environment2.id, host1.reload.puppet.environment_id
32
+ assert_equal environment2.id, host2.reload.puppet.environment_id
33
+ assert_equal 'Updated hosts: changed environment', flash[:success]
34
+ end
35
+
36
+ test 'should inherit the hostgroup environment if *inherit from hostgroup* selected' do
37
+ @request.env['HTTP_REFERER'] = '/hosts'
38
+ setup_user 'edit', 'hosts'
39
+
40
+ params = { host_ids: [host1.id, host2.id], environment: { id: 'inherit' } }
41
+ post :update_multiple_environment, params: params, session: set_session_user(:one)
42
+
43
+ assert_equal hostgroup.puppet.environment_id, host1.reload.puppet.environment_id
44
+ assert_equal hostgroup.puppet.environment_id, host2.reload.puppet.environment_id
45
+ end
46
+
47
+ describe '#edit' do
48
+ setup { @routes = Rails.application.routes }
49
+
50
+ test 'lookup value and description should be html escaped' do
51
+ skip 'Needs complete migration to be done' unless ForemanPuppet.extracted_from_core?
52
+ FactoryBot.create(:puppetclass_lookup_key,
53
+ default_value: "<script>alert('hacked!');</script>",
54
+ description: "<script>alert('hacked!');</script>",
55
+ puppetclass: host1.puppet.puppetclasses.first)
56
+ get :edit, params: { id: host1.to_param }, session: set_session_user
57
+ assert_not response.body.include?('<script>alert(')
58
+ assert_includes response.body, '&lt;script&gt;alert('
59
+ assert_equal 2, response.body.scan('&lt;script&gt;alert(').count
60
+ end
61
+ end
62
+
63
+ describe '#hostgroup_or_environment_selected' do
64
+ let(:hostgroup) { FactoryBot.create(:hostgroup, :with_puppet_enc, organizations: [org], locations: [loc]) }
65
+
66
+ test 'choosing only one of hostgroup or environment renders classes' do
67
+ post :hostgroup_or_environment_selected, params: {
68
+ host_id: nil,
69
+ host: {
70
+ puppet_attributes: {
71
+ environment_id: environment1.id,
72
+ },
73
+ },
74
+ }, session: set_session_user, xhr: true
75
+ assert_response :success
76
+ assert_template partial: 'hosts/_form_puppet_enc_tab'
77
+ end
78
+
79
+ test 'choosing both hostgroup and environment renders classes' do
80
+ post :hostgroup_or_environment_selected, params: {
81
+ host_id: host1.id,
82
+ host: {
83
+ hostgroup_id: hostgroup.id,
84
+ puppet_attributes: {
85
+ environment_id: environment1.id,
86
+ },
87
+ },
88
+ }, session: set_session_user, xhr: true
89
+ assert_response :success
90
+ assert_template partial: 'hosts/_form_puppet_enc_tab'
91
+ end
92
+
93
+ test 'should not escape lookup values on environment change' do
94
+ host = FactoryBot.create(:host, :with_puppet_enc, :with_puppetclass)
95
+
96
+ host.environment.locations = [host.location]
97
+ host.environment.organizations = [host.organization]
98
+
99
+ lookup_key = FactoryBot.create(:puppetclass_lookup_key, :array, default_value: %w[a b],
100
+ override: true,
101
+ puppetclass: host.puppet.puppetclasses.first,
102
+ overrides: { "fqdn=#{host.fqdn}" => %w[c d] })
103
+ lookup_value = lookup_key.lookup_values.first
104
+
105
+ # sending exactly what the host form would send which is lookup_value.value_before_type_cast
106
+ lk_params = { 'lookup_values_attributes' => { lookup_key.id.to_s => { 'value' => lookup_value.value_before_type_cast,
107
+ 'id' => lookup_value.id,
108
+ 'lookup_key_id' => lookup_key.id,
109
+ '_destroy' => false } } }
110
+ params = {
111
+ host_id: host.id,
112
+ host: host.attributes.merge(lk_params),
113
+ }
114
+
115
+ # environment change calls puppetclass_parameters which caused the extra escaping
116
+ post :puppetclass_parameters, params: params, session: set_session_user, xhr: true
117
+
118
+ # if this was escaped during refresh_host the value in response.body after unescapeHTML would include "[\\\"c\\\",\\\"d\\\"]"
119
+ assert_includes CGI.unescapeHTML(response.body), '["c","d"]'
120
+ end
121
+ end
122
+
123
+ describe 'setting puppet proxy on multiple hosts' do
124
+ test 'should change the puppet proxy' do
125
+ proxy = FactoryBot.create(:puppet_smart_proxy)
126
+
127
+ @request.env['HTTP_REFERER'] = '/hosts'
128
+ params = { host_ids: [host1.id, host2.id], proxy: { proxy_id: proxy.id } }
129
+
130
+ setup_user 'edit', 'hosts'
131
+ post :update_multiple_puppet_proxy, params: params, session: set_session_user(:one)
132
+
133
+ assert_empty flash[:error]
134
+
135
+ set_admin
136
+ [host1, host2].each do |host|
137
+ assert_equal proxy, host.reload.puppet_proxy
138
+ end
139
+ end
140
+
141
+ test 'should clear the puppet proxy of multiple hosts' do
142
+ @request.env['HTTP_REFERER'] = '/hosts'
143
+
144
+ params = { host_ids: [host1.id, host2.id], proxy: { proxy_id: '' } }
145
+
146
+ setup_user 'edit', 'hosts'
147
+ post :update_multiple_puppet_proxy, params: params, session: set_session_user(:one)
148
+
149
+ assert_empty flash[:error]
150
+
151
+ set_admin
152
+ [host1, host2].each do |host|
153
+ assert_nil host.reload.puppet_proxy
154
+ end
155
+ end
156
+ end
157
+
158
+ describe '#externalNodes' do
159
+ test 'externalNodes should render YAML hashes correctly' do
160
+ HostInfoProviders::PuppetInfo.any_instance.expects(:classes_info_hash).returns(
161
+ 'dhcp' => {
162
+ 'bootfiles' => [
163
+ { 'name' => 'foo', 'mount_point' => '/bar' }.with_indifferent_access,
164
+ { 'name' => 'john', 'mount_point' => '/doe' }.with_indifferent_access,
165
+ ],
166
+ }
167
+ ).at_least_once
168
+
169
+ get :externalNodes, params: { name: host1.name, format: 'yml' }, session: set_session_user
170
+ assert_response :success
171
+ enc = nil
172
+ as_admin { enc = host1.info.deep_stringify_keys.to_yaml }
173
+ assert_equal enc, response.body
174
+ end
175
+
176
+ test 'externalNodes should render correctly when format text/html is given' do
177
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
178
+ get :externalNodes, params: { name: host1.name }, session: set_session_user
179
+ assert_response :success
180
+ as_admin { @enc = host1.info.to_yaml }
181
+ assert_equal "<pre>#{ERB::Util.html_escape(@enc)}</pre>", response.body
182
+ end
183
+
184
+ test 'externalNodes should render yml request correctly' do
185
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
186
+ get :externalNodes, params: { name: host1.name, format: 'yml' }, session: set_session_user
187
+ assert_response :success
188
+ as_admin { @enc = host1.info.deep_stringify_keys.to_yaml(line_width: -1) }
189
+ assert_equal @enc, response.body
190
+ end
191
+
192
+ test 'when ":restrict_registered_smart_proxies" is false, HTTP requests should be able to get externalNodes' do
193
+ User.current = nil
194
+ Setting[:restrict_registered_smart_proxies] = false
195
+ SETTINGS[:require_ssl] = false
196
+
197
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
198
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
199
+ assert_response :success
200
+ end
201
+
202
+ test 'hosts with a registered smart proxy on should get externalNodes successfully' do
203
+ User.current = nil
204
+ Setting[:restrict_registered_smart_proxies] = true
205
+ Setting[:require_ssl_smart_proxies] = false
206
+
207
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
208
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
209
+ assert_response :success
210
+ end
211
+
212
+ test 'hosts without a registered smart proxy on should not be able to get externalNodes' do
213
+ User.current = nil
214
+ Setting[:restrict_registered_smart_proxies] = true
215
+ Setting[:require_ssl_smart_proxies] = false
216
+
217
+ Resolv.any_instance.stubs(:getnames).returns(['another.host'])
218
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
219
+ assert_equal 403, @response.status
220
+ end
221
+
222
+ test 'hosts with a registered smart proxy and SSL cert should get externalNodes successfully' do
223
+ User.current = nil
224
+ Setting[:restrict_registered_smart_proxies] = true
225
+ Setting[:require_ssl_smart_proxies] = true
226
+
227
+ @request.env['HTTPS'] = 'on'
228
+ @request.env['SSL_CLIENT_S_DN'] = 'CN=else.where'
229
+ @request.env['SSL_CLIENT_VERIFY'] = 'SUCCESS'
230
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
231
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
232
+ assert_response :success
233
+ end
234
+
235
+ test 'hosts in trusted hosts list and SSL cert should get externalNodes successfully' do
236
+ User.current = nil
237
+ Setting[:restrict_registered_smart_proxies] = true
238
+ Setting[:require_ssl_smart_proxies] = true
239
+ Setting[:trusted_hosts] = ['else.where']
240
+
241
+ @request.env['HTTPS'] = 'on'
242
+ @request.env['SSL_CLIENT_S_DN'] = 'CN=else.where'
243
+ @request.env['SSL_CLIENT_VERIFY'] = 'SUCCESS'
244
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
245
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
246
+ assert_response :success
247
+ end
248
+
249
+ test 'hosts with comma-separated SSL DN should get externalNodes successfully' do
250
+ User.current = nil
251
+ Setting[:restrict_registered_smart_proxies] = true
252
+ Setting[:require_ssl_smart_proxies] = true
253
+ Setting[:trusted_hosts] = ['foreman.example']
254
+
255
+ @request.env['HTTPS'] = 'on'
256
+ @request.env['SSL_CLIENT_S_DN'] = 'CN=foreman.example,OU=PUPPET,O=FOREMAN,ST=North Carolina,C=US'
257
+ @request.env['SSL_CLIENT_VERIFY'] = 'SUCCESS'
258
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
259
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
260
+ assert_response :success
261
+ end
262
+
263
+ test 'hosts with slash-separated SSL DN should get externalNodes successfully' do
264
+ User.current = nil
265
+ Setting[:restrict_registered_smart_proxies] = true
266
+ Setting[:require_ssl_smart_proxies] = true
267
+ Setting[:trusted_hosts] = ['foreman.linux.lab.local']
268
+
269
+ @request.env['HTTPS'] = 'on'
270
+ @request.env['SSL_CLIENT_S_DN'] = '/C=US/ST=NC/L=City/O=Example/OU=IT/CN=foreman.linux.lab.local/emailAddress=user@example.com'
271
+ @request.env['SSL_CLIENT_VERIFY'] = 'SUCCESS'
272
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
273
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
274
+ assert_response :success
275
+ end
276
+
277
+ test 'hosts without a registered smart proxy but with an SSL cert should not be able to get externalNodes' do
278
+ User.current = nil
279
+ Setting[:restrict_registered_smart_proxies] = true
280
+ Setting[:require_ssl_smart_proxies] = true
281
+
282
+ @request.env['HTTPS'] = 'on'
283
+ @request.env['SSL_CLIENT_S_DN'] = 'CN=another.host'
284
+ @request.env['SSL_CLIENT_VERIFY'] = 'SUCCESS'
285
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
286
+ assert_equal 403, @response.status
287
+ end
288
+
289
+ test 'hosts with an unverified SSL cert should not be able to get externalNodes' do
290
+ User.current = nil
291
+ Setting[:restrict_registered_smart_proxies] = true
292
+ Setting[:require_ssl_smart_proxies] = true
293
+
294
+ @request.env['HTTPS'] = 'on'
295
+ @request.env['SSL_CLIENT_S_DN'] = 'CN=else.where'
296
+ @request.env['SSL_CLIENT_VERIFY'] = 'FAILURE'
297
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
298
+ assert_equal 403, @response.status
299
+ end
300
+
301
+ test 'when "require_ssl_smart_proxies" and "require_ssl" are true, HTTP requests should not be able to get externalNodes' do
302
+ User.current = nil
303
+ Setting[:restrict_registered_smart_proxies] = true
304
+ Setting[:require_ssl_smart_proxies] = true
305
+ SETTINGS[:require_ssl] = true
306
+
307
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
308
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
309
+ assert_equal 403, @response.status
310
+ end
311
+
312
+ test 'when "require_ssl_smart_proxies" is true and "require_ssl" is false, HTTP requests should be able to get externalNodes' do
313
+ User.current = nil
314
+ # since require_ssl_smart_proxies is only applicable to HTTPS connections, both should be set
315
+ Setting[:restrict_registered_smart_proxies] = true
316
+ Setting[:require_ssl_smart_proxies] = true
317
+ SETTINGS[:require_ssl] = false
318
+
319
+ Resolv.any_instance.stubs(:getnames).returns(['else.where'])
320
+ get :externalNodes, params: { name: host1.name, format: 'yml' }
321
+ assert_response :success
322
+ end
323
+
324
+ test 'authenticated users over HTTP should be able to get externalNodes' do
325
+ Setting[:restrict_registered_smart_proxies] = true
326
+ Setting[:require_ssl_smart_proxies] = true
327
+ SETTINGS[:require_ssl] = false
328
+
329
+ Resolv.any_instance.stubs(:getnames).returns(['users.host'])
330
+ get :externalNodes, params: { name: host1.name, format: 'yml' }, session: set_session_user
331
+ assert_response :success
332
+ end
333
+
334
+ test 'authenticated users over HTTPS should be able to get externalNodes' do
335
+ Setting[:restrict_registered_smart_proxies] = true
336
+ Setting[:require_ssl_smart_proxies] = true
337
+ SETTINGS[:require_ssl] = false
338
+
339
+ Resolv.any_instance.stubs(:getnames).returns(['users.host'])
340
+ @request.env['HTTPS'] = 'on'
341
+ get :externalNodes, params: { name: host1.name, format: 'yml' }, session: set_session_user
342
+ assert_response :success
343
+ end
344
+ end
345
+ end
346
+ end