foreman_wreckingball 3.1.0 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -1
  3. data/app/assets/javascripts/foreman_wreckingball/modal.js +0 -1
  4. data/app/assets/javascripts/foreman_wreckingball/status_hosts_table.js +2 -2
  5. data/app/assets/javascripts/foreman_wreckingball/status_row.js +17 -0
  6. data/app/controllers/foreman_wreckingball/hosts_controller.rb +65 -35
  7. data/app/lib/actions/foreman_wreckingball/host/remediate_spectre_v2.rb +58 -0
  8. data/app/models/concerns/foreman_wreckingball/host_extensions.rb +10 -25
  9. data/app/models/concerns/foreman_wreckingball/host_status_extensions.rb +13 -0
  10. data/app/models/concerns/foreman_wreckingball/user_extensions.rb +12 -0
  11. data/app/models/concerns/foreman_wreckingball/usergroup_extensions.rb +18 -0
  12. data/app/models/concerns/foreman_wreckingball/vmware_facet_host_extensions.rb +10 -0
  13. data/app/models/foreman_wreckingball/cpu_hot_add_status.rb +8 -0
  14. data/app/models/foreman_wreckingball/hardware_version_status.rb +8 -0
  15. data/app/models/foreman_wreckingball/operatingsystem_status.rb +8 -0
  16. data/app/models/foreman_wreckingball/spectre_v2_status.rb +17 -1
  17. data/app/models/foreman_wreckingball/tools_status.rb +8 -0
  18. data/app/models/foreman_wreckingball/vmware_facet.rb +1 -5
  19. data/app/services/foreman_wreckingball/vmware_cluster_importer.rb +1 -6
  20. data/app/views/foreman_wreckingball/hosts/_status_dashboard_content.erb +10 -21
  21. data/app/views/foreman_wreckingball/hosts/_status_row_hosts_table.html.erb +1 -1
  22. data/app/views/foreman_wreckingball/hosts/status_dashboard.html.erb +1 -0
  23. data/app/views/foreman_wreckingball/hosts/status_managed_hosts_dashboard.html.erb +49 -0
  24. data/config/environments/production.rb +7 -0
  25. data/config/routes.rb +1 -0
  26. data/lib/foreman_wreckingball/engine.rb +21 -6
  27. data/lib/foreman_wreckingball/version.rb +1 -1
  28. data/test/actions/foreman_wreckingball/host/remediate_spectre_v2_test.rb +62 -0
  29. data/test/controllers/foreman_wreckingball/hosts_controller_test.rb +180 -12
  30. data/test/factories/foreman_wreckingball_factories.rb +32 -0
  31. data/test/factories/host.rb +8 -0
  32. data/test/factories/task.rb +17 -0
  33. data/test/integration/hosts_status_dashboard_test.rb +50 -0
  34. data/test/integration/hosts_status_managed_hosts_test.rb +93 -0
  35. data/test/integration_test_plugin_helper.rb +12 -0
  36. data/test/models/host_status_test.rb +22 -0
  37. data/test/models/host_test.rb +64 -5
  38. data/test/models/usergroup_test.rb +25 -0
  39. data/test/test_plugin_helper.rb +17 -0
  40. data/test/unit/foreman_wreckingball/vmware_cluster_importer_test.rb +17 -2
  41. metadata +23 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 76ab3d42565e2f65a0fd36a5e1f54c610793f02d8a520cde857dbdb19c3db0c3
4
- data.tar.gz: 8dacc5958e40ecd78d06e28baeaff904ae5f26965d4eed3d3b56deeb924dbad6
3
+ metadata.gz: de6be68d909a39447b86fc7b8ce9f372cc12c929364910205beac6d8dc244829
4
+ data.tar.gz: 2908a912c935764b978d0f094306ecbad458c70c9bed5138051f52d73f83697f
5
5
  SHA512:
6
- metadata.gz: 8eca4ac7802cfdd392505b99e2233f288210246da2b7936a167aa809e26e8696b44a27b6da983fda2548389c88a3dc84c4aaee9cd544e859ff43e2aef6aca41d
7
- data.tar.gz: a7e4f716a844d628d29abbbd1443c9010b0f543d32fa047d9e4d566fcc6c8c4a29c9988686656dbc10034a5a1e2bd47ffd33131899ece6b2087719309600b1d3
6
+ metadata.gz: d4de761155c5e670000022056211ad3f4064a303914b869c8624f40679b723e6d90d7aa2ba3f156c9f2b535a02a9474cf8c817b7e967f537e7ca8e843a764a84
7
+ data.tar.gz: 84e82bf20310a20cde12e50dcacd5fb84ab638e1eabf280aefbf3f1cb3d9a1253cbb57136dbb29ea618e95425380cd296a011f8dc40738b7339837833fd5bfa5
data/README.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # ForemanWreckingball
2
2
 
3
+ [<img src="https://opensourcelogos.aws.dmtech.cloud/dmTECH_opensource_logo%401x.svg" height="21" width="130">](https://www.dmtech.de/)
4
+
3
5
  This is a plugin for Foreman that adds several VMware related status checks to your Hosts in Foreman. For performance reasons, these checks are only run periodically.
4
6
 
5
7
  ## Compatibility
@@ -23,7 +25,7 @@ Fork and send a Pull Request. Thanks!
23
25
 
24
26
  ## Copyright
25
27
 
26
- Copyright (c) 2018 dm-drogerie markt GmbH & Co. KG https://dm.de
28
+ Copyright (c) 2018 dmTECH GmbH, [dmtech.de](https://www.dmtech.de/)
27
29
 
28
30
  This program is free software: you can redistribute it and/or modify
29
31
  it under the terms of the GNU General Public License as published by
@@ -39,4 +39,3 @@ function show_modal(element, url) {
39
39
  });
40
40
  return false;
41
41
  }
42
-
@@ -1,7 +1,7 @@
1
1
  $(document).ready(() => {
2
2
  $.fn.dataTable.ext.errMode = 'none';
3
- $('.status-row.list-group-item').one('click', (a, b, c) => {
4
- $(a.currentTarget).find('table.status-hosts').each((_index, element) => {
3
+ $('.status-row.list-group-item').one('click', function() {
4
+ $(this).find('table.status-hosts').each((_index, element) => {
5
5
  $(element).dataTable({
6
6
  searching: false,
7
7
  ordering: false,
@@ -0,0 +1,17 @@
1
+ $(document).ready(() => {
2
+ // click the list-view heading then expand a row
3
+ $('.list-group-item-header').click(function(event) {
4
+ if(!$(event.target).is('button, a, input, .fa-ellipsis-v')) {
5
+ $(this).find('.fa-angle-right').toggleClass('fa-angle-down')
6
+ .end().parent().toggleClass('list-view-pf-expand-active')
7
+ .find('.list-group-item-container').toggleClass('hidden');
8
+ }
9
+ });
10
+
11
+ // click the close button, hide the expand row and remove the active status
12
+ $('.list-group-item-container .close').click(function() {
13
+ $(this).parent().addClass('hidden')
14
+ .parent().removeClass('list-view-pf-expand-active')
15
+ .find('.fa-angle-right').removeClass('fa-angle-down');
16
+ });
17
+ });
@@ -16,23 +16,18 @@ module ForemanWreckingball
16
16
  before_action :find_status, :only => [:submit_remediate, :schedule_remediate]
17
17
 
18
18
  def status_dashboard
19
- statuses = [
20
- ToolsStatus,
21
- OperatingsystemStatus,
22
- CpuHotAddStatus,
23
- SpectreV2Status,
24
- HardwareVersionStatus
25
- ]
26
-
27
- @newest_data = Host.authorized(:view_hosts, Host).joins(:vmware_facet).maximum('vmware_facets.updated_at')
28
- @data = statuses.map do |status|
29
- host_association = status.host_association
30
- counter = Host.authorized(:view_hosts, Host)
31
- .joins(host_association)
32
- .includes(host_association)
33
- .map { |host| host.public_send(host_association).to_global }
34
- .group_by { |global_status| global_status }
35
- .each_with_object({}) { |(global_status, items), hash| hash[global_status] = items.size }
19
+ @newest_data = Host.authorized(:view_hosts).joins(:vmware_facet).maximum('vmware_facets.updated_at')
20
+ host_ids = Host.authorized(:view_hosts)
21
+ .try { |query| params[:owned_only] ? query.owned_by_current_user_or_group_with_current_user : query }
22
+ .pluck(:id)
23
+
24
+ @data = HostStatus.wreckingball_statuses.map do |status|
25
+ counter = status.where(host_id: host_ids)
26
+ .select(:status)
27
+ .group(:status)
28
+ .count
29
+ .transform_keys { |key| status.to_global(key) }
30
+
36
31
  {
37
32
  name: status.status_name,
38
33
  description: status.description,
@@ -47,25 +42,55 @@ module ForemanWreckingball
47
42
  end
48
43
  end
49
44
 
45
+ def status_managed_hosts_dashboard
46
+ @hosts = Host::Managed.authorized(:view_hosts, Host)
47
+ .try { |query| params[:owned_only] ? query.owned_by_current_user_or_group_with_current_user : query }
48
+
49
+ compute_resources = ComputeResource.where(:type => 'Foreman::Model::Vmware')
50
+
51
+ # get all vms by compute resource id
52
+ vms_by_compute_resource_id = {}
53
+ # NOTE The call to ComputeResource#vms may slow things down
54
+ compute_resources.each { |cr| vms_by_compute_resource_id[cr.id] = cr.vms(eager_loading: true) }
55
+
56
+ vms_by_uuid = vms_by_compute_resource_id.values.flatten.group_by(&:uuid)
57
+
58
+ # Find all hosts with duplicate VMs
59
+ @duplicate_vms = vms_by_uuid.select { |_uuid, vms| vms.size > 1 }
60
+
61
+ @missing_hosts = []
62
+ @different_hosts = []
63
+
64
+ @hosts.each do |host|
65
+ next unless host.compute_resource_id
66
+
67
+ # find the compute resource id of the host in the vm map
68
+ cr_id, _vms = vms_by_compute_resource_id.find { |_cr_id, vms| vms.find { |vm| vm.uuid == host.uuid } }
69
+
70
+ if cr_id.nil?
71
+ # No compute resource id is found, vSphere does not have the vm uuid
72
+ @missing_hosts << host
73
+ elsif cr_id != host.compute_resource_id
74
+ # The host uuid is found in a different compute resource
75
+ @different_hosts << host
76
+ end
77
+ end
78
+ end
79
+
50
80
  # ajax method
51
81
  def status_hosts
52
- statuses_map = {
53
- vmware_tools_status_object: ForemanWreckingball::ToolsStatus,
54
- vmware_operatingsystem_status_object: ForemanWreckingball::OperatingsystemStatus,
55
- vmware_cpu_hot_add_status_object: ForemanWreckingball::CpuHotAddStatus,
56
- vmware_spectre_v2_status_object: ForemanWreckingball::SpectreV2Status,
57
- vmware_hardware_version_status_object: ForemanWreckingball::HardwareVersionStatus
58
- }
59
-
60
- @status = statuses_map[params[:status].to_sym]
82
+ @status = HostStatus.find_wreckingball_status_by_host_association(params.fetch(:status).to_sym)
83
+
61
84
  all_hosts = Host.authorized(:view_hosts, Host)
62
85
  .joins(@status.host_association)
86
+ .try { |query| params[:owned_only] ? query.owned_by_current_user_or_group_with_current_user : query }
63
87
  .includes(@status.host_association, :vmware_facet, :environment)
88
+ .where.not('host_status.status': @status.global_ok_list)
64
89
  .preload(:owner)
65
90
  .order(:name)
66
- @count = all_hosts.count
67
- @hosts = all_hosts.reject { |h| h.send(@status.host_association).to_global == HostStatus::Global::OK }
68
- .paginate(page: params.fetch(:page, 1), per_page: params.fetch(:per_page, 100))
91
+
92
+ @count = all_hosts.size
93
+ @hosts = all_hosts.paginate(page: params.fetch(:page, 1), per_page: params.fetch(:per_page, 100))
69
94
 
70
95
  respond_to do |format|
71
96
  format.json do
@@ -77,11 +102,16 @@ module ForemanWreckingball
77
102
  end
78
103
 
79
104
  def refresh_status_dashboard
80
- flash[:success] = _('Refresh Compute Resource data task was successfully scheduled.')
81
- task = User.as_anonymous_admin do
82
- ::ForemanTasks.async_task(::Actions::ForemanWreckingball::Vmware::ScheduleVmwareSync)
105
+ if ForemanTasks::Task.active.where(label: ::Actions::ForemanWreckingball::Vmware::ScheduleVmwareSync.to_s).empty?
106
+ flash[:success] = _('Refresh Compute Resource data task was successfully scheduled.')
107
+ task = User.as_anonymous_admin do
108
+ ::ForemanTasks.async_task(::Actions::ForemanWreckingball::Vmware::ScheduleVmwareSync)
109
+ end
110
+ redirect_to(foreman_tasks_task_path(task.id))
111
+ else
112
+ flash[:warning] = _('Refresh Compute Resource data task is already running. Please wait for the running task to finish.')
113
+ redirect_to status_dashboard_hosts_path
83
114
  end
84
- redirect_to(foreman_tasks_task_path(task.id))
85
115
  end
86
116
 
87
117
  def schedule_remediate
@@ -89,7 +119,7 @@ module ForemanWreckingball
89
119
  end
90
120
 
91
121
  def submit_remediate
92
- raise Foreman::Exception, 'VMware Status can not be remediated.' unless @status.class.respond_to?(:supports_remediate?) && @status.class.supports_remediate?
122
+ raise Foreman::Exception, _('VMware Status can not be remediated.') unless @status.class.respond_to?(:supports_remediate?) && @status.class.supports_remediate?
93
123
  task = User.as_anonymous_admin do
94
124
  triggering = ::ForemanTasks::Triggering.new_from_params(triggering_params)
95
125
  if triggering.future?
@@ -119,7 +149,7 @@ module ForemanWreckingball
119
149
 
120
150
  def action_permission
121
151
  case params[:action]
122
- when 'status_dashboard'
152
+ when 'status_dashboard', 'status_hosts'
123
153
  'view'
124
154
  when 'refresh_status_dashboard'
125
155
  'refresh_vmware_status'
@@ -0,0 +1,58 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Actions
4
+ module ForemanWreckingball
5
+ module Host
6
+ class RemediateSpectreV2 < Actions::EntryAction
7
+ middleware.use Actions::Middleware::KeepCurrentUser
8
+
9
+ def delay(delay_options, host)
10
+ action_subject(host)
11
+ super(delay_options, host)
12
+ end
13
+
14
+ def plan(host)
15
+ action_subject(host)
16
+ plan_self
17
+ end
18
+
19
+ def run
20
+ host = ::Host.find(input[:host][:id])
21
+
22
+ initially_powered_on = host.power.ready?
23
+ output[:initially_powered_on] = initially_powered_on
24
+
25
+ vm = host.compute_object
26
+
27
+ if initially_powered_on
28
+ vm.stop
29
+ vm.wait_for { power_state == 'poweredOff' }
30
+ fail _('Could not shut down VM.') if vm.ready?
31
+ end
32
+
33
+ vm.start if vm && initially_powered_on
34
+
35
+ state = host.refresh_vmware_facet!
36
+ output[:state] = state
37
+ end
38
+
39
+ def humanized_name
40
+ _('Power-Cycle VM')
41
+ end
42
+
43
+ def humanized_input
44
+ input[:host] && input[:host][:name]
45
+ end
46
+
47
+ def append_error(message)
48
+ output[:errors] ||= []
49
+ output[:errors] << message
50
+ end
51
+
52
+ def rescue_strategy
53
+ Dynflow::Action::Rescue::Skip
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
@@ -6,31 +6,16 @@ module ForemanWreckingball
6
6
  include ForemanTasks::Concerns::ActionSubject
7
7
 
8
8
  included do
9
- has_one :vmware_tools_status_object,
10
- :class_name => 'ForemanWreckingball::ToolsStatus',
11
- :foreign_key => 'host_id',
12
- :inverse_of => :host,
13
- :dependent => :destroy
14
- has_one :vmware_operatingsystem_status_object,
15
- :class_name => 'ForemanWreckingball::OperatingsystemStatus',
16
- :foreign_key => 'host_id',
17
- :inverse_of => :host,
18
- :dependent => :destroy
19
- has_one :vmware_cpu_hot_add_status_object,
20
- :class_name => 'ForemanWreckingball::CpuHotAddStatus',
21
- :foreign_key => 'host_id',
22
- :inverse_of => :host,
23
- :dependent => :destroy
24
- has_one :vmware_spectre_v2_status_object,
25
- :class_name => 'ForemanWreckingball::SpectreV2Status',
26
- :foreign_key => 'host_id',
27
- :inverse_of => :host,
28
- :dependent => :destroy
29
- has_one :vmware_hardware_version_status_object,
30
- :class_name => 'ForemanWreckingball::HardwareVersionStatus',
31
- :foreign_key => 'host_id',
32
- :inverse_of => :host,
33
- :dependent => :destroy
9
+ ForemanWreckingball::Engine::WRECKINGBALL_STATUSES.map(&:constantize).each do |status|
10
+ has_one(status.host_association, class_name: status.to_s,
11
+ foreign_key: 'host_id',
12
+ inverse_of: :host,
13
+ dependent: :destroy)
14
+ end
15
+
16
+ scope :owned_by_current_user, -> { where(owner_type: 'User', owner_id: User.current.id) }
17
+ scope :owned_by_group_with_current_user, -> { where(owner_type: 'Usergroup', owner_id: User.current.usergroup_ids_with_parents) }
18
+ scope :owned_by_current_user_or_group_with_current_user, -> { owned_by_current_user.or(owned_by_group_with_current_user) }
34
19
  end
35
20
 
36
21
  def action_input_key
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ForemanWreckingball
4
+ module HostStatusExtensions
5
+ def wreckingball_statuses
6
+ status_registry.select { |s| s.to_s.start_with?('ForemanWreckingball') }
7
+ end
8
+
9
+ def find_wreckingball_status_by_host_association(host_association)
10
+ wreckingball_statuses.find { |s| s.host_association == host_association }
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ForemanWreckingball
4
+ module UserExtensions
5
+ def usergroup_ids_with_parents
6
+ ids = []
7
+ ids << usergroup_ids
8
+ ids << usergroups.map(&:parent_usergroup_ids)
9
+ ids.flatten.uniq
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ForemanWreckingball
4
+ module UsergroupExtensions
5
+ def parent_usergroup_ids
6
+ @parent_usergroup_ids ||= get_parent_ids(parent_ids)
7
+ end
8
+
9
+ private
10
+
11
+ def get_parent_ids(member_ids, result_ids = parent_ids)
12
+ return result_ids if member_ids.empty?
13
+
14
+ new_parent_ids = UsergroupMember.usergroup_memberships.where(member_id: member_ids).pluck(:usergroup_id)
15
+ get_parent_ids(new_parent_ids, result_ids + new_parent_ids)
16
+ end
17
+ end
18
+ end
@@ -8,6 +8,16 @@ module ForemanWreckingball
8
8
  has_one :vmware_facet, :class_name => '::ForemanWreckingball::VmwareFacet', :foreign_key => :host_id, :inverse_of => :host, :dependent => :destroy
9
9
 
10
10
  before_provision :queue_vmware_facet_refresh
11
+
12
+ scoped_search on: :hardware_version, relation: :vmware_facet, rename: :vsphere_hardware_version, complete_value: true, only_explicit: true
13
+ scoped_search on: :guest_id, relation: :vmware_facet, rename: :vsphere_guest_id, complete_value: true, only_explicit: true
14
+ scoped_search on: :cpus, relation: :vmware_facet, rename: :vsphere_cpus, complete_value: true, only_explicit: true
15
+ scoped_search on: :corespersocket, relation: :vmware_facet, rename: :vsphere_corespersocket, complete_value: true, only_explicit: true
16
+ scoped_search on: :memory_mb, relation: :vmware_facet, rename: :vsphere_memory_mb, complete_value: true, only_explicit: true
17
+ scoped_search on: :power_state, relation: :vmware_facet, rename: :vsphere_power_state, only_explicit: true,
18
+ complete_value: ForemanWreckingball::VmwareFacet::VALID_POWER_STATES.map { |status| [status, ForemanWreckingball::VmwareFacet.power_states[status]] }.to_h
19
+ scoped_search on: :tools_state, relation: :vmware_facet, rename: :vsphere_tools_state, only_explicit: true,
20
+ complete_value: ForemanWreckingball::VmwareFacet::VALID_GUEST_STATUSES.map { |status| [status, ForemanWreckingball::VmwareFacet.tools_states[status]] }.to_h
11
21
  end
12
22
 
13
23
  def refresh_vmware_facet!
@@ -26,6 +26,10 @@ module ForemanWreckingball
26
26
  end
27
27
 
28
28
  def to_global(_options = {})
29
+ self.class.to_global(status)
30
+ end
31
+
32
+ def self.to_global(status)
29
33
  case status
30
34
  when PERFORMANCE_DEGRATION
31
35
  HostStatus::Global::ERROR
@@ -34,6 +38,10 @@ module ForemanWreckingball
34
38
  end
35
39
  end
36
40
 
41
+ def self.global_ok_list
42
+ [OK]
43
+ end
44
+
37
45
  def to_label(_options = {})
38
46
  case status
39
47
  when PERFORMANCE_DEGRATION
@@ -34,6 +34,10 @@ module ForemanWreckingball
34
34
  end
35
35
 
36
36
  def to_global(_options = {})
37
+ self.class.to_global(status)
38
+ end
39
+
40
+ def self.to_global(status)
37
41
  case status
38
42
  when OUTOFDATE
39
43
  HostStatus::Global::WARN
@@ -42,6 +46,10 @@ module ForemanWreckingball
42
46
  end
43
47
  end
44
48
 
49
+ def self.global_ok_list
50
+ [OK]
51
+ end
52
+
45
53
  def to_label(_options = {})
46
54
  case status
47
55
  when OUTOFDATE
@@ -34,6 +34,10 @@ module ForemanWreckingball
34
34
  end
35
35
 
36
36
  def to_global(_options = {})
37
+ self.class.to_global(status)
38
+ end
39
+
40
+ def self.to_global(status)
37
41
  case status
38
42
  when MISMATCH
39
43
  HostStatus::Global::WARN
@@ -42,6 +46,10 @@ module ForemanWreckingball
42
46
  end
43
47
  end
44
48
 
49
+ def self.global_ok_list
50
+ [OK]
51
+ end
52
+
45
53
  def to_label(_options = {})
46
54
  case status
47
55
  when MISMATCH
@@ -18,7 +18,15 @@ module ForemanWreckingball
18
18
  end
19
19
 
20
20
  def self.supports_remediate?
21
- false
21
+ true
22
+ end
23
+
24
+ def self.dangerous_remediate?
25
+ true
26
+ end
27
+
28
+ def self.remediate_action
29
+ ::Actions::ForemanWreckingball::Host::RemediateSpectreV2
22
30
  end
23
31
 
24
32
  def to_status(_options = {})
@@ -26,6 +34,10 @@ module ForemanWreckingball
26
34
  end
27
35
 
28
36
  def to_global(_options = {})
37
+ self.class.to_global(status)
38
+ end
39
+
40
+ def self.to_global(status)
29
41
  case status
30
42
  when MISSING
31
43
  HostStatus::Global::ERROR
@@ -34,6 +46,10 @@ module ForemanWreckingball
34
46
  end
35
47
  end
36
48
 
49
+ def self.global_ok_list
50
+ [ENABLED]
51
+ end
52
+
37
53
  def to_label(_options = {})
38
54
  case status
39
55
  when MISSING
@@ -26,6 +26,10 @@ module ForemanWreckingball
26
26
  end
27
27
 
28
28
  def to_global(_options = {})
29
+ self.class.to_global(status)
30
+ end
31
+
32
+ def self.to_global(status)
29
33
  case status
30
34
  when VmwareFacet.tools_states[:toolsOk], POWERDOWN
31
35
  HostStatus::Global::OK
@@ -36,6 +40,10 @@ module ForemanWreckingball
36
40
  end
37
41
  end
38
42
 
43
+ def self.global_ok_list
44
+ [VmwareFacet.tools_states[:toolsOk], POWERDOWN]
45
+ end
46
+
39
47
  def to_label(_options = {})
40
48
  return N_('Powered down') if status == POWERDOWN
41
49
  host.vmware_facet.tools_state_label
@@ -57,11 +57,7 @@ module ForemanWreckingball
57
57
  end
58
58
 
59
59
  def refresh_statuses
60
- host.get_status(::ForemanWreckingball::ToolsStatus).refresh!
61
- host.get_status(::ForemanWreckingball::CpuHotAddStatus).refresh!
62
- host.get_status(::ForemanWreckingball::OperatingsystemStatus).refresh!
63
- host.get_status(::ForemanWreckingball::SpectreV2Status).refresh!
64
- host.get_status(::ForemanWreckingball::HardwareVersionStatus).refresh!
60
+ ::HostStatus.wreckingball_statuses.each { |status| host.get_status(status).refresh! }
65
61
  host.refresh_global_status!
66
62
  end
67
63
 
@@ -18,12 +18,7 @@ module ForemanWreckingball
18
18
  end
19
19
 
20
20
  def delete_removed_clusters
21
- delete_query = ::ForemanWreckingball::VmwareCluster.where(:compute_resource => compute_resource).where.not(:name => cluster_names)
22
- counters[:deleted] = if ActiveRecord::Base.connection.adapter_name.downcase.starts_with? 'mysql'
23
- ::ForemanWreckingball::VmwareCluster.where(:id => delete_query.pluck(:id)).delete_all
24
- else
25
- delete_query.delete_all
26
- end
21
+ counters[:deleted] = ::ForemanWreckingball::VmwareCluster.where(compute_resource: compute_resource).where.not(name: cluster_names).destroy_all
27
22
  end
28
23
 
29
24
  def create_new_clusters
@@ -5,6 +5,16 @@
5
5
  )
6
6
  %>
7
7
 
8
+ <%= title_actions(
9
+ button_group(
10
+ if params[:owned_only]
11
+ link_to _('Show all hosts'), status_dashboard_hosts_path, class: 'btn btn-default'
12
+ else
13
+ link_to _('Show only owned hosts'), status_dashboard_hosts_path(owned_only: true), class: 'btn btn-default'
14
+ end
15
+ )
16
+ ) %>
17
+
8
18
  <div class="list-group list-view-pf list-view-pf-equalized-column" style="max-height: initial;">
9
19
  <% @data.each_with_index do |status, idx| %>
10
20
  <%=
@@ -19,24 +29,3 @@
19
29
  %>
20
30
  <% end %>
21
31
  </div>
22
- <script>
23
- $(document).ready(function () {
24
- // click the list-view heading then expand a row
25
- $(".list-group-item-header").click(function(event){
26
- if(!$(event.target).is("button, a, input, .fa-ellipsis-v")){
27
- $(this).find(".fa-angle-right").toggleClass("fa-angle-down")
28
- .end().parent().toggleClass("list-view-pf-expand-active")
29
- .find(".list-group-item-container").toggleClass("hidden");
30
- } else {
31
- }
32
- })
33
-
34
- // click the close button, hide the expand row and remove the active status
35
- $(".list-group-item-container .close").on("click", function (){
36
- $(this).parent().addClass("hidden")
37
- .parent().removeClass("list-view-pf-expand-active")
38
- .find(".fa-angle-right").removeClass("fa-angle-down");
39
- })
40
-
41
- });
42
- </script>
@@ -1,6 +1,6 @@
1
1
  <%= content_tag :table, id: status,
2
2
  class: 'table table-striped table-fixed status-hosts',
3
- 'data-hosts-url': ajax_status_dashboard_hosts_path(status) do %>
3
+ 'data-hosts-url': ajax_status_dashboard_hosts_path(status, owned_only: params[:owned_only]) do %>
4
4
  <%= content_tag :thead do %>
5
5
  <%= content_tag :tr do %>
6
6
  <%= content_tag :th, _('Hostname') %>
@@ -2,6 +2,7 @@
2
2
  <% javascript 'foreman_wreckingball/modal' %>
3
3
  <% javascript 'foreman_wreckingball/status_hosts_table' %>
4
4
  <% stylesheet 'foreman_wreckingball/status_hosts_table' %>
5
+ <% javascript 'foreman_wreckingball/status_row' %>
5
6
  <% javascript 'foreman_tasks/trigger_form' %>
6
7
  <% stylesheet 'foreman_tasks/trigger_form' %>
7
8
 
@@ -0,0 +1,49 @@
1
+ <% title _('VMware Managed Hosts Overview') %>
2
+ <% javascript 'foreman_wreckingball/modal' %>
3
+ <% javascript 'foreman_wreckingball/status_hosts_table' %>
4
+ <% stylesheet 'foreman_wreckingball/status_hosts_table' %>
5
+
6
+ <%= title_actions(
7
+ button_group(
8
+ if params[:owned_only]
9
+ link_to _('Show all hosts'), status_managed_hosts_dashboard_hosts_path, class: 'btn btn-default'
10
+ else
11
+ link_to _('Show only owned hosts'), status_managed_hosts_dashboard_hosts_path(owned_only: true), class: 'btn btn-default'
12
+ end
13
+ )
14
+ ) %>
15
+
16
+ <% if @missing_hosts.any? %>
17
+ <div id="missing_vms">
18
+ <h2>List of hosts not found in vSphere</h2>
19
+ <div class="list-group list-view-pf list-view-pf-equalized-column" style="max-height: initial;">
20
+ <% @missing_hosts.each do |host| %>
21
+ <div><%= host.name %></div>
22
+ <% end %>
23
+ </div>
24
+ </div>
25
+ <% end %>
26
+
27
+ <% if @duplicate_vms.any? %>
28
+ <div id="duplicate_vms">
29
+ <h2>List of VMs with same uuid</h2>
30
+ <div class="list-group list-view-pf list-view-pf-equalized-column" style="max-height: initial;">
31
+ <% @duplicate_vms.each do |uuid, hosts| %>
32
+ <% hosts.each do |host| %>
33
+ <div><%= host.uuid %> - <%= host.name %></div>
34
+ <% end %>
35
+ <% end %>
36
+ </div>
37
+ </div>
38
+ <% end %>
39
+
40
+ <% if @different_hosts.any? %>
41
+ <div id="different_vms">
42
+ <h2>List of VMs associated with different compute resources</h2>
43
+ <div class="list-group list-view-pf list-view-pf-equalized-column" style="max-height: initial;">
44
+ <% @different_hosts.each do |host| %>
45
+ <div><%= host.uuid %> - <%= host.name %></div>
46
+ <% end %>
47
+ </div>
48
+ </div>
49
+ <% end %>
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ require Rails.root.join('config', 'environments', 'production.rb')
4
+
5
+ Foreman::Application.configure do
6
+ config.assets.js_compressor = Uglifier.new(harmony: true) if defined?(Uglifier)
7
+ end
data/config/routes.rb CHANGED
@@ -10,6 +10,7 @@ Rails.application.routes.draw do
10
10
  end
11
11
  collection do
12
12
  get :status_dashboard
13
+ get :status_managed_hosts_dashboard
13
14
  get 'status_dashboard/hosts(/:status)', as: :ajax_status_dashboard, action: :status_hosts, defaults: { format: :json }
14
15
  put :refresh_status_dashboard
15
16
  end