foreman_rh_cloud 4.0.24.1 → 4.0.27

Sign up to get free protection for your applications and to get access to all the features.
Files changed (97) hide show
  1. checksums.yaml +4 -4
  2. data/app/controllers/api/v2/rh_cloud/inventory_controller.rb +4 -1
  3. data/app/controllers/foreman_inventory_upload/cloud_status_controller.rb +26 -0
  4. data/app/controllers/insights_cloud/api/machine_telemetries_controller.rb +18 -4
  5. data/app/controllers/insights_cloud/hits_controller.rb +0 -1
  6. data/app/services/foreman_rh_cloud/cloud_auth.rb +4 -0
  7. data/app/services/foreman_rh_cloud/cloud_ping_service.rb +83 -0
  8. data/app/services/foreman_rh_cloud/cloud_request_forwarder.rb +15 -3
  9. data/app/services/foreman_rh_cloud/remediations_retriever.rb +5 -0
  10. data/config/Gemfile.lock.gh_test +74 -84
  11. data/config/rh_cert-api_chain.pem +74 -0
  12. data/config/routes.rb +3 -1
  13. data/lib/foreman_inventory_upload/generators/queries.rb +0 -16
  14. data/lib/foreman_inventory_upload/generators/tags.rb +2 -1
  15. data/lib/foreman_rh_cloud/engine.rb +2 -1
  16. data/lib/foreman_rh_cloud/version.rb +1 -1
  17. data/lib/foreman_rh_cloud.rb +16 -1
  18. data/lib/insights_cloud/async/insights_client_status_aging.rb +4 -0
  19. data/lib/insights_cloud/async/insights_full_sync.rb +9 -0
  20. data/lib/insights_cloud/async/insights_generate_notifications.rb +4 -0
  21. data/lib/insights_cloud/async/insights_resolutions_sync.rb +16 -2
  22. data/lib/insights_cloud/async/insights_rules_sync.rb +15 -2
  23. data/lib/insights_cloud.rb +4 -0
  24. data/lib/inventory_sync/async/inventory_full_sync.rb +9 -0
  25. data/lib/inventory_sync/async/inventory_hosts_sync.rb +9 -0
  26. data/lib/inventory_sync/async/inventory_scheduled_sync.rb +4 -0
  27. data/lib/inventory_sync/async/inventory_self_host_sync.rb +13 -0
  28. data/lib/inventory_sync/async/query_inventory_job.rb +4 -0
  29. data/lib/tasks/rh_cloud_inventory.rake +2 -9
  30. data/package.json +1 -1
  31. data/test/controllers/insights_cloud/api/machine_telemetries_controller_test.rb +20 -39
  32. data/test/controllers/inventory_upload/cloud_status_controller_test.rb +44 -0
  33. data/test/jobs/insights_full_sync_test.rb +1 -0
  34. data/test/jobs/insights_resolutions_sync_test.rb +11 -1
  35. data/test/jobs/insights_rules_sync_test.rb +1 -0
  36. data/test/jobs/inventory_full_sync_test.rb +10 -0
  37. data/test/jobs/inventory_hosts_sync_test.rb +1 -0
  38. data/test/jobs/inventory_self_host_sync_test.rb +1 -0
  39. data/test/test_plugin_helper.rb +53 -0
  40. data/test/unit/foreman_rh_cloud_self_host_test.rb +28 -0
  41. data/test/unit/services/foreman_rh_cloud/cloud_request_forwarder_test.rb +29 -34
  42. data/test/unit/services/foreman_rh_cloud/cloud_status_service_test.rb +66 -0
  43. data/test/unit/services/foreman_rh_cloud/template_renderer_helper_test.rb +1 -0
  44. data/test/unit/tags_generator_test.rb +41 -0
  45. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/EmptyState/EmptyState.js +1 -1
  46. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/EmptyState/__tests__/__snapshots__/EmptyState.test.js.snap +1 -2
  47. data/webpack/ForemanInventoryUpload/Components/FileDownload/FileDownload.js +3 -1
  48. data/webpack/ForemanInventoryUpload/Components/FileDownload/__tests__/__snapshots__/FileDownload.test.js.snap +2 -1
  49. data/webpack/ForemanInventoryUpload/Components/InventoryFilter/InventoryFilter.js +1 -2
  50. data/webpack/ForemanInventoryUpload/Components/InventoryFilter/InventoryFilterConstants.js +3 -1
  51. data/webpack/ForemanInventoryUpload/Components/InventorySettings/InventorySettings.scss +0 -4
  52. data/webpack/ForemanInventoryUpload/Components/PageHeader/PageTitle.js +12 -0
  53. data/webpack/ForemanInventoryUpload/Components/PageHeader/__tests__/__snapshots__/PageTitle.test.js.snap +10 -0
  54. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/CloudPingModal/index.js +144 -0
  55. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/CloudPingModal/index.scss +5 -0
  56. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/PageDescription/PageDescription.js +2 -2
  57. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/SyncButton/components/Modal.js +1 -1
  58. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/SyncButton/components/Toast.js +2 -2
  59. data/webpack/ForemanInventoryUpload/Components/StatusChart/StatusChart.js +4 -3
  60. data/webpack/ForemanInventoryUpload/ForemanInventoryConstants.js +2 -0
  61. data/webpack/ForemanInventoryUpload/SubscriptionsPageExtension/InventoryAutoUpload/InventoryAutoUpload.js +3 -1
  62. data/webpack/InsightsCloudSync/Components/InsightsHeader/InsightsHeader.scss +5 -1
  63. data/webpack/InsightsCloudSync/Components/InsightsHeader/index.js +6 -6
  64. data/webpack/InsightsCloudSync/Components/InsightsSettings/InsightsSettings.js +9 -5
  65. data/webpack/InsightsCloudSync/Components/InsightsSettings/__tests__/__snapshots__/InsightsSettings.test.js.snap +6 -6
  66. data/webpack/InsightsCloudSync/Components/InsightsSettings/insightsSettings.scss +1 -14
  67. data/webpack/InsightsCloudSync/Components/InsightsTable/InsightsTable.js +4 -22
  68. data/webpack/InsightsCloudSync/Components/InsightsTable/InsightsTableConstants.js +25 -4
  69. data/webpack/InsightsCloudSync/Components/InsightsTable/InsightsTableSelectors.js +0 -3
  70. data/webpack/InsightsCloudSync/Components/InsightsTable/Pagination.js +51 -0
  71. data/webpack/InsightsCloudSync/Components/InsightsTable/SelectAllAlert.js +1 -1
  72. data/webpack/InsightsCloudSync/Components/InsightsTable/__tests__/__snapshots__/InsightsTable.test.js.snap +3 -68
  73. data/webpack/InsightsCloudSync/Components/InsightsTable/table.scss +10 -0
  74. data/webpack/InsightsCloudSync/Components/RemediationModal/RemediationModal.js +11 -10
  75. data/webpack/InsightsCloudSync/Components/RemediationModal/RemediationModal.scss +14 -0
  76. data/webpack/InsightsCloudSync/Components/RemediationModal/index.js +0 -2
  77. data/webpack/InsightsCloudSync/Components/ToolbarDropdown.js +32 -0
  78. data/webpack/InsightsCloudSync/Components/__tests__/__snapshots__/InsightsHeader.test.js.snap +5 -5
  79. data/webpack/InsightsCloudSync/InsightsCloudSync.js +19 -13
  80. data/webpack/InsightsCloudSync/InsightsCloudSync.scss +82 -2
  81. data/webpack/InsightsCloudSync/__snapshots__/InsightsCloudSync.test.js.snap +16 -6
  82. data/webpack/InsightsHostDetailsTab/InsightsTab.js +3 -2
  83. data/webpack/InsightsHostDetailsTab/InsightsTab.scss +4 -4
  84. data/webpack/InsightsHostDetailsTab/components/ListItem/ListItem.js +9 -7
  85. data/webpack/common/Switcher/HelpLabel.js +1 -1
  86. data/webpack/common/Switcher/SwitcherPF4.js +1 -1
  87. data/webpack/common/Switcher/SwitcherPF4.scss +6 -7
  88. data/webpack/common/Switcher/__tests__/__snapshots__/HelpLabel.test.js.snap +1 -1
  89. data/webpack/common/Switcher/__tests__/__snapshots__/SwitcherPF4.test.js.snap +1 -1
  90. metadata +16 -24
  91. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/InsightsSyncSwitcher.fixtures.js +0 -1
  92. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/InsightsSyncSwitcher.js +0 -45
  93. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/__tests__/InsightsSyncSwitcher.test.js +0 -17
  94. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/__tests__/__snapshots__/InsightsSyncSwitcher.test.js.snap +0 -38
  95. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/index.js +0 -1
  96. data/webpack/InsightsCloudSync/Components/InsightsSyncSwitcher/insightsSyncSwitcher.scss +0 -3
  97. data/webpack/InsightsCloudSync/Components/RemediationModal/RemediateButton.js +0 -59
@@ -45,26 +45,10 @@ module ForemanInventoryUpload
45
45
  )
46
46
  end
47
47
 
48
- def self.for_report(portal_user)
49
- org_ids = organizations_for_user(portal_user).pluck(:id)
50
- for_org(org_ids)
51
- end
52
-
53
48
  def self.for_org(organization_id, use_batches: true)
54
49
  base_query = for_slice(Host.unscoped.where(organization_id: organization_id))
55
50
  use_batches ? base_query.in_batches(of: ForemanInventoryUpload.slice_size) : base_query
56
51
  end
57
-
58
- def self.organizations_for_user(portal_user)
59
- Organization
60
- .joins(:telemetry_configuration)
61
- .where(
62
- redhat_access_telemetry_configurations: {
63
- portal_user: portal_user,
64
- enable_telemetry: true,
65
- }
66
- )
67
- end
68
52
  end
69
53
  end
70
54
  end
@@ -19,7 +19,8 @@ module ForemanInventoryUpload
19
19
  def generate_parameters
20
20
  return [] unless Setting[:include_parameter_tags]
21
21
 
22
- (@host.host_inherited_params_objects || []).map { |item| [item.name, item.value] }
22
+ (@host.host_params || {})
23
+ .select { |_name, value| value.present? || value.is_a?(FalseClass) }
23
24
  end
24
25
 
25
26
  private
@@ -1,5 +1,4 @@
1
1
  require 'katello'
2
- require 'redhat_access'
3
2
  require 'foreman_ansible'
4
3
 
5
4
  module ForemanRhCloud
@@ -43,6 +42,8 @@ module ForemanRhCloud
43
42
  Foreman::Plugin.register :foreman_rh_cloud do
44
43
  requires_foreman '>= 2.3'
45
44
 
45
+ apipie_documented_controllers ["#{ForemanRhCloud::Engine.root}/app/controllers/api/v2/**/*.rb"]
46
+
46
47
  # Add permissions
47
48
  security_block :foreman_rh_cloud do
48
49
  permission(
@@ -1,3 +1,3 @@
1
1
  module ForemanRhCloud
2
- VERSION = '4.0.24.1'.freeze
2
+ VERSION = '4.0.27'.freeze
3
3
  end
@@ -98,6 +98,21 @@ module ForemanRhCloud
98
98
 
99
99
  # For testing purposes we can override the default hostname with an environment variable SATELLITE_RH_CLOUD_FOREMAN_HOST
100
100
  def self.foreman_host
101
- @foreman_host ||= ::Host.unscoped.friendly.find(ENV['SATELLITE_RH_CLOUD_FOREMAN_HOST'] || ::SmartProxy.default_capsule.name)
101
+ @foreman_host ||= begin
102
+ fullname = foreman_host_name
103
+ ::Host.unscoped.friendly.find(fullname)
104
+ rescue ActiveRecord::RecordNotFound
105
+ # fullname didn't work. Let's try shortname
106
+ shortname = /(?<shortname>[^\.]*)\.?.*/.match(fullname)[:shortname]
107
+ ::Host.unscoped.friendly.find(shortname)
108
+ end
109
+ end
110
+
111
+ def self.foreman_host_name
112
+ ENV['SATELLITE_RH_CLOUD_FOREMAN_HOST'] || ::SmartProxy.default_capsule.name
113
+ end
114
+
115
+ def self.legacy_insights_ca
116
+ "#{ForemanRhCloud::Engine.root}/config/rh_cert-api_chain.pem"
102
117
  end
103
118
  end
@@ -18,6 +18,10 @@ module InsightsCloud
18
18
  def logger
19
19
  action_logger
20
20
  end
21
+
22
+ def rescue_strategy_for_self
23
+ Dynflow::Action::Rescue::Fail
24
+ end
21
25
  end
22
26
  end
23
27
  end
@@ -6,6 +6,11 @@ module InsightsCloud
6
6
  include ::ForemanRhCloud::CloudAuth
7
7
 
8
8
  def plan
9
+ unless cloud_auth_available?
10
+ logger.debug('Cloud authentication is not available, skipping insights sync')
11
+ return
12
+ end
13
+
9
14
  sequence do
10
15
  # This can be turned off when we enable automatic status syncs
11
16
  # This step will query cloud inventory to retrieve inventory uuids for each host
@@ -113,6 +118,10 @@ module InsightsCloud
113
118
 
114
119
  match || { id: nil }
115
120
  end
121
+
122
+ def rescue_strategy_for_self
123
+ Dynflow::Action::Rescue::Fail
124
+ end
116
125
  end
117
126
  end
118
127
  end
@@ -53,6 +53,10 @@ module InsightsCloud
53
53
  }
54
54
  )
55
55
  end
56
+
57
+ def rescue_strategy_for_self
58
+ Dynflow::Action::Rescue::Fail
59
+ end
56
60
  end
57
61
  end
58
62
  end
@@ -7,11 +7,21 @@ module InsightsCloud
7
7
 
8
8
  RULE_ID_REGEX = /[^:]*:(?<id>.*)/
9
9
 
10
+ def plan
11
+ unless cloud_auth_available?
12
+ logger.debug('Cloud authentication is not available, skipping resolutions sync')
13
+ return
14
+ end
15
+
16
+ plan_self
17
+ end
18
+
10
19
  def run
11
20
  InsightsResolution.transaction do
12
21
  InsightsResolution.delete_all
13
- api_response = query_insights_resolutions(relevant_rules)
14
- write_resolutions(api_response)
22
+ rule_ids = relevant_rules
23
+ api_response = query_insights_resolutions(rule_ids) unless rule_ids.empty?
24
+ write_resolutions(api_response) if api_response
15
25
  end
16
26
  end
17
27
 
@@ -61,6 +71,10 @@ module InsightsCloud
61
71
  def to_rule_id(resolution_rule_id)
62
72
  RULE_ID_REGEX.match(resolution_rule_id).named_captures.fetch('id', resolution_rule_id)
63
73
  end
74
+
75
+ def rescue_strategy_for_self
76
+ Dynflow::Action::Rescue::Fail
77
+ end
64
78
  end
65
79
  end
66
80
  end
@@ -6,8 +6,17 @@ module InsightsCloud
6
6
  include ::ForemanRhCloud::CloudAuth
7
7
 
8
8
  def plan
9
- plan_self
10
- plan_resolutions
9
+ unless cloud_auth_available?
10
+ logger.debug('Cloud authentication is not available, skipping rules sync')
11
+ return
12
+ end
13
+
14
+ # since the tasks are not connected, we need to force sequence execution here
15
+ # to make sure we don't run resolutions until we synced all our rules
16
+ sequence do
17
+ plan_self
18
+ plan_resolutions
19
+ end
11
20
  end
12
21
 
13
22
  def plan_resolutions
@@ -66,6 +75,10 @@ module InsightsCloud
66
75
  rating: rule_hash['rating'],
67
76
  }
68
77
  end
78
+
79
+ def rescue_strategy_for_self
80
+ Dynflow::Action::Rescue::Fail
81
+ end
69
82
  end
70
83
  end
71
84
  end
@@ -28,4 +28,8 @@ module InsightsCloud
28
28
  def self.remediation_rule_id(rule_id)
29
29
  "advisor:#{rule_id}"
30
30
  end
31
+
32
+ def self.enable_client_param
33
+ 'host_registration_insights'
34
+ end
31
35
  end
@@ -5,6 +5,11 @@ module InventorySync
5
5
  set_callback :step, :around, :update_statuses_batch
6
6
 
7
7
  def plan(organization)
8
+ unless cloud_auth_available?
9
+ logger.debug('Cloud authentication is not available, skipping inventory hosts sync')
10
+ return
11
+ end
12
+
8
13
  plan_self(organization_id: organization.id)
9
14
  end
10
15
 
@@ -34,6 +39,10 @@ module InventorySync
34
39
  host_statuses[:sync] += results.touched.size
35
40
  end
36
41
 
42
+ def rescue_strategy_for_self
43
+ Dynflow::Action::Rescue::Fail
44
+ end
45
+
37
46
  private
38
47
 
39
48
  def update_hosts_status(status_hashes, touched)
@@ -5,6 +5,11 @@ module InventorySync
5
5
  set_callback :step, :around, :create_facets
6
6
 
7
7
  def plan
8
+ unless cloud_auth_available?
9
+ logger.debug('Cloud authentication is not available, skipping inventory hosts sync')
10
+ return
11
+ end
12
+
8
13
  # by default the tasks will be executed concurrently
9
14
  plan_self
10
15
  plan_self_host_sync
@@ -23,6 +28,10 @@ module InventorySync
23
28
  results
24
29
  end
25
30
 
31
+ def rescue_strategy_for_self
32
+ Dynflow::Action::Rescue::Fail
33
+ end
34
+
26
35
  private
27
36
 
28
37
  def add_missing_insights_facets(uuids_hash)
@@ -24,6 +24,10 @@ module InventorySync
24
24
  def logger
25
25
  action_logger
26
26
  end
27
+
28
+ def rescue_strategy_for_self
29
+ Dynflow::Action::Rescue::Fail
30
+ end
27
31
  end
28
32
  end
29
33
  end
@@ -3,6 +3,15 @@ module InventorySync
3
3
  class InventorySelfHostSync < QueryInventoryJob
4
4
  set_callback :step, :around, :create_facets
5
5
 
6
+ def plan
7
+ unless cloud_auth_available?
8
+ logger.debug('Cloud authentication is not available, skipping self host sync')
9
+ return
10
+ end
11
+
12
+ plan_self
13
+ end
14
+
6
15
  def create_facets
7
16
  # get the results from the event
8
17
  results = yield
@@ -11,6 +20,10 @@ module InventorySync
11
20
  results
12
21
  end
13
22
 
23
+ def rescue_strategy_for_self
24
+ Dynflow::Action::Rescue::Fail
25
+ end
26
+
14
27
  private
15
28
 
16
29
  def add_missing_insights_facet(uuids_hash)
@@ -50,6 +50,10 @@ module InventorySync
50
50
  def request_url
51
51
  ForemanInventoryUpload.inventory_export_url
52
52
  end
53
+
54
+ def rescue_strategy_for_self
55
+ Dynflow::Action::Rescue::Fail
56
+ end
53
57
  end
54
58
  end
55
59
  end
@@ -19,7 +19,6 @@ namespace :rh_cloud_inventory do
19
19
  end
20
20
  desc 'Generate inventory report to be sent to Red Hat cloud'
21
21
  task generate: :environment do
22
- portal_user = ENV['portal_user']
23
22
  organizations = [ENV['organization_id']]
24
23
  base_folder = ENV['target'] || Dir.pwd
25
24
 
@@ -29,18 +28,12 @@ namespace :rh_cloud_inventory do
29
28
  puts "Using #{base_folder} for the output"
30
29
  end
31
30
 
32
- if portal_user.empty? && organizations.empty?
33
- puts "Must specify either portal_user or organization_id"
31
+ if organizations.empty?
32
+ puts "Must specify organization_id"
34
33
  return
35
34
  end
36
35
 
37
36
  User.as_anonymous_admin do
38
- if portal_user
39
- puts "Generating report for all organizations associated with #{portal_user}"
40
- base_folder = File.join(base_folder, portal_user)
41
- organizations = ForemanInventoryUpload::Generators::Queries.organizations_for_user(portal_user).pluck(:id)
42
- end
43
-
44
37
  organizations.each do |organization|
45
38
  target = File.join(base_folder, ForemanInventoryUpload.facts_archive_name(organization))
46
39
  archived_report_generator = ForemanInventoryUpload::Generators::ArchivedReport.new(target, Logger.new(STDOUT))
data/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "foreman_rh_cloud",
3
- "version": "4.0.24.1",
3
+ "version": "4.0.27",
4
4
  "description": "Inventory Upload =============",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -2,7 +2,13 @@ require 'test_plugin_helper'
2
2
 
3
3
  module InsightsCloud::Api
4
4
  class MachineTelemetriesControllerTest < ActionController::TestCase
5
+ setup do
6
+ FactoryBot.create(:common_parameter, name: InsightsCloud.enable_client_param, key_type: 'boolean', value: true)
7
+ end
8
+
5
9
  context '#forward_request' do
10
+ include MockCerts
11
+
6
12
  setup do
7
13
  @body = 'Cloud response body'
8
14
  @http_req = RestClient::Request.new(:method => 'GET', :url => 'http://test.theforeman.org')
@@ -12,38 +18,9 @@ module InsightsCloud::Api
12
18
  User.current = ::Katello::CpConsumerUser.new(:uuid => host.subscription_facet.uuid, :login => host.subscription_facet.uuid)
13
19
  InsightsCloud::Api::MachineTelemetriesController.any_instance.stubs(:upstream_owner).returns({ 'uuid' => 'abcdefg' })
14
20
 
15
- @cert1 = "-----BEGIN CERTIFICATE-----\r\n" +
16
- "MIIFdDCCA1ygAwIBAgIJAM5Uqykb3EAtMA0GCSqGSIb3DQEBCwUAME8xCzAJBgNV\r\n" +
17
- "BAYTAklMMREwDwYDVQQIDAhUZWwgQXZpdjEUMBIGA1UECgwLVGhlIEZvcmVtYW4x\r\n" +
18
- "FzAVBgNVBAMMDnRoZWZvcmVtYW4ub3JnMB4XDTE4MDMyNDEyMzYyOFoXDTI4MDMy\r\n" +
19
- "MTEyMzYyOFowTzELMAkGA1UEBhMCSUwxETAPBgNVBAgMCFRlbCBBdml2MRQwEgYD\r\n" +
20
- "VQQKDAtUaGUgRm9yZW1hbjEXMBUGA1UEAwwOdGhlZm9yZW1hbi5vcmcwggIiMA0G\r\n" +
21
- "CSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDF04/s4h+BgHPG1HDZ/sDlYq925pkc\r\n" +
22
- "RTVAfnE2EXDAmZ6W4Q9ueDY65MHe3ZWO5Dg72kNSP2sK9kRI7Dk5CAFOgyw1rH8t\r\n" +
23
- "Hd1+0xp/lv6e4SvSYghxIL68vFe0ftKkm1usqejBM5ZTgKr7JCI+XSIN36F65Kde\r\n" +
24
- "c+vxwBnayuhP04r9/aaE/709SXML4eRVYW8I3qFy9FPtUOm+bY8U2PIv5fHayqbG\r\n" +
25
- "cL/4t3+MCtMhHJsLzdBXya+1P5t+HcKjUNlmwoUF961YAktVuEFloGd0RMRlqF3/\r\n" +
26
- "itU3QNlXgA5QBIciE5VPr/PiqgMC3zgd5avjF4OribZ+N9AATLiQMW78il5wSfcc\r\n" +
27
- "kQjU9ChOLrzku455vQ8KE4bc0qvpCWGfUah6MvL9JB+TQkRl/8kxl0b9ZinIvJDH\r\n" +
28
- "ynVMb4cB/TDEjrjOfzn9mWLH0ZJqjmc2bER/G12WQxOaYLxdVwRStD3Yh6PtiFWu\r\n" +
29
- "sXOk19UOTVkeuvGFVtvzLfEwQ1lDEo7+VBQz8FG/HBu2Hpq3IwCFrHuicikwjQJk\r\n" +
30
- "nfturgD0rBOKEc1qWNZRCvovYOLL6ihvv5Orujsx5ZCHOAtnVNxkvIlFt2RS45LF\r\n" +
31
- "MtPJyhAc6SjitllfUEirxprsbmeSZqrIfzcGaEhgOSnyik1WMv6bYiqPfBg8Fzjh\r\n" +
32
- "vOCbtiDNPmvgOwIDAQABo1MwUTAdBgNVHQ4EFgQUtkAgQopsTtG9zSG3MgW2IxHD\r\n" +
33
- "MDwwHwYDVR0jBBgwFoAUtkAgQopsTtG9zSG3MgW2IxHDMDwwDwYDVR0TAQH/BAUw\r\n" +
34
- "AwEB/zANBgkqhkiG9w0BAQsFAAOCAgEAJq7iN+ZroRBweNhvUobxs75bLIV6tNn1\r\n" +
35
- "MdNHDRA+hezwf+gxHZhFyaAHfTpst2/9leK5Qe5Zd6gZLr3E5/8ppQuRod72H39B\r\n" +
36
- "vxMlG5zxDss0WMo3vZeKZbTY6QhXi/lY2IZ6OGV4feSvCsYxn27GTjjrRUSLFeHH\r\n" +
37
- "JVemCwCDMavaE3+OIY4v2P4FcG+MjUvfOB9ahI24TWL7YgrsNVmJjCILq+EeUj0t\r\n" +
38
- "Gde1SXVyLkqt7PoxHRJAE0BCEMJSnjxaVB329acJgeehBUxjj4CCPqtDxtbz9HEH\r\n" +
39
- "mOKfNdaKpFor+DUeEKUWVGnr9U9xOaC+Ws+oX7MIEUCDM7p2ob4JwcjnFs1jZgHh\r\n" +
40
- "Hwig+i7doTlc701PvKWO96fuNHK3B3/jTb1fVvSZ49O/RvY1VWODdUdxWmXGHNh3\r\n" +
41
- "LoR8tSPEb46lC2DXGaIQumqQt8PnBG+vL1qkQa1SGTV7dJ8TTbxbv0S+sS+igkk9\r\n" +
42
- "zsIEK8Ea3Ep935cXximz0faAAKHSA+It+xHLAyDtqy2KaAEBgGsBuuWlUfK6TaP3\r\n" +
43
- "Gwdjct3y4yYUO45lUsUfHqX8vk/4ttW5zYeDiW+HArJz+9VUXNbEdury4kGuHgBj\r\n" +
44
- "xHD4Bsul65+hHZ9QywKU26F1A6TLkYpQ2rk/Dx9LGICM4m4IlHjWJPFsQdtkyOor\r\n" +
45
- "osxMtcaZZ1E=\r\n" +
46
- "-----END CERTIFICATE-----"
21
+ setup_certs_expectation do
22
+ InsightsCloud::Api::MachineTelemetriesController.any_instance.stubs(:candlepin_id_cert)
23
+ end
47
24
  end
48
25
 
49
26
  test "should respond with response from cloud" do
@@ -63,13 +40,6 @@ module InsightsCloud::Api
63
40
  ::ForemanRhCloud::CloudRequestForwarder.any_instance.expects(:execute_cloud_request).with do |opts|
64
41
  opts[:headers][:content_type] == 'application/json'
65
42
  end.returns(res)
66
- InsightsCloud::Api::MachineTelemetriesController.any_instance.expects(:candlepin_id_cert)
67
- .returns(
68
- {
69
- cert: @cert1,
70
- key: OpenSSL::PKey::RSA.new(1024).to_pem,
71
- }
72
- )
73
43
  InsightsCloud::Api::MachineTelemetriesController.any_instance.expects(:cp_owner_id).returns('123')
74
44
 
75
45
  post :forward_request, as: :json, params: { "path" => "static/v1/test", "machine_telemetry" => {"foo" => "bar"} }
@@ -99,6 +69,17 @@ module InsightsCloud::Api
99
69
  assert_equal 502, @response.status
100
70
  assert_equal 'Authentication to the Insights Service failed.', JSON.parse(@response.body)['message']
101
71
  end
72
+
73
+ test "should forward errors to the client" do
74
+ net_http_resp = Net::HTTPResponse.new(1.0, 500, "TEST_RESPONSE")
75
+ res = RestClient::Response.create(@body, net_http_resp, @http_req)
76
+ ::ForemanRhCloud::CloudRequestForwarder.any_instance.stubs(:execute_cloud_request).raises(RestClient::InternalServerError.new(res))
77
+
78
+ get :forward_request, params: { "path" => "platform/module-update-router/v1/channel" }
79
+ assert_equal 500, @response.status
80
+ assert_equal 'Cloud request failed', JSON.parse(@response.body)['message']
81
+ assert_match /#{@body}/, JSON.parse(@response.body)['response']
82
+ end
102
83
  end
103
84
 
104
85
  context '#branch_info' do
@@ -0,0 +1,44 @@
1
+ require 'test_plugin_helper'
2
+
3
+ class CloudStatusControllerTest < ActionController::TestCase
4
+ include MockCerts
5
+ tests ForemanInventoryUpload::CloudStatusController
6
+
7
+ test 'return ping status hash for each organization' do
8
+ organizations = FactoryBot.create_list(:organization, 2)
9
+ user = users(:admin)
10
+ User.stubs(:current).returns(user)
11
+ user.stubs(:my_organizations).returns(organizations)
12
+
13
+ ForemanRhCloud::CloudPingService::TokenPing.any_instance.expects(:execute_cloud_request).returns(
14
+ RestClient::Response.new('TEST RESPONSE')
15
+ )
16
+
17
+ setup_certs_expectation do
18
+ ForemanRhCloud::CloudPingService::CertPing.any_instance.expects(:candlepin_id_cert).with { |actual| actual.id == organizations[0].id }
19
+ end
20
+ ForemanRhCloud::CloudPingService::CertPing.any_instance.expects(:execute_cloud_request).returns(
21
+ RestClient::Response.new('TEST RESPONSE ORG 0')
22
+ )
23
+
24
+ setup_certs_expectation do
25
+ ForemanRhCloud::CloudPingService::CertPing.any_instance.expects(:candlepin_id_cert).with { |actual| actual.id == organizations[1].id }
26
+ end
27
+
28
+ ForemanRhCloud::CloudPingService::CertPing.any_instance.expects(:execute_cloud_request).returns(
29
+ RestClient::Response.new('TEST RESPONSE ORG 1')
30
+ )
31
+
32
+ get :index, session: set_session_user
33
+
34
+ assert_response :success
35
+ actual = JSON.parse(response.body)
36
+ assert_not_nil (actual_ping = actual['ping'])
37
+ assert actual_ping['token_auth']['success']
38
+ assert_nil actual_ping['token_auth']['error']
39
+ assert actual_ping['cert_auth'][0]['success']
40
+ assert_nil actual_ping['cert_auth'][0]['error']
41
+ assert actual_ping['cert_auth'][1]['success']
42
+ assert_nil actual_ping['cert_auth'][1]['error']
43
+ end
44
+ end
@@ -7,6 +7,7 @@ class InsightsFullSyncTest < ActiveSupport::TestCase
7
7
  setup do
8
8
  InsightsCloud::Async::InsightsFullSync.any_instance.stubs(:plan_rules_sync)
9
9
  InsightsCloud::Async::InsightsFullSync.any_instance.stubs(:plan_notifications)
10
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'MOCK_TOKEN')
10
11
 
11
12
  uuid1 = 'accdf444-5628-451d-bf3e-cf909ad72756'
12
13
  @host1 = FactoryBot.create(:host, :managed, name: 'host1')
@@ -1,4 +1,4 @@
1
- require 'test_helper'
1
+ require 'test_plugin_helper'
2
2
  require 'foreman_tasks/test_helpers'
3
3
 
4
4
  class InsightsResolutionsSyncTest < ActiveSupport::TestCase
@@ -63,6 +63,7 @@ class InsightsResolutionsSyncTest < ActiveSupport::TestCase
63
63
  }
64
64
 
65
65
  @rule = FactoryBot.create(:insights_rule, rule_id: 'network_tcp_connection_hang|NETWORK_TCP_CONNECTION_HANG_WARN')
66
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'MOCK_TOKEN')
66
67
  end
67
68
 
68
69
  test 'Resolutions data is replaced with data from cloud' do
@@ -74,4 +75,13 @@ class InsightsResolutionsSyncTest < ActiveSupport::TestCase
74
75
  assert_equal 5, InsightsResolution.all.count
75
76
  assert_equal 2, @rule.resolutions.count
76
77
  end
78
+
79
+ test 'Skips pinging the cloud if no rule ids were found' do
80
+ InsightsCloud::Async::InsightsResolutionsSync.any_instance.expects(:query_insights_resolutions).never
81
+ InsightsRule.all.delete_all
82
+
83
+ ForemanTasks.sync_task(InsightsCloud::Async::InsightsResolutionsSync)
84
+
85
+ assert_equal 0, InsightsResolution.all.count
86
+ end
77
87
  end
@@ -112,6 +112,7 @@ class InsightsRulesSyncTest < ActiveSupport::TestCase
112
112
  @hit = FactoryBot.create(:insights_hit, host_id: @host.id)
113
113
 
114
114
  InsightsCloud::Async::InsightsRulesSync.any_instance.stubs(:plan_resolutions)
115
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'MOCK_TOKEN')
115
116
  end
116
117
 
117
118
  test 'Hits data is replaced with data from cloud' do
@@ -242,6 +242,7 @@ class InventoryFullSyncTest < ActiveSupport::TestCase
242
242
  end
243
243
 
244
244
  test 'Host status should be SYNC for inventory hosts' do
245
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'TEST TOKEN')
245
246
  InventorySync::Async::InventoryFullSync.any_instance.expects(:query_inventory).returns(@inventory)
246
247
 
247
248
  ForemanTasks.sync_task(InventorySync::Async::InventoryFullSync, @host2.organization)
@@ -253,6 +254,7 @@ class InventoryFullSyncTest < ActiveSupport::TestCase
253
254
  end
254
255
 
255
256
  test 'Host status should be DISCONNECT for hosts that are not returned from cloud' do
257
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'TEST TOKEN')
256
258
  InventorySync::Async::InventoryFullSync.any_instance.expects(:query_inventory).returns(@inventory)
257
259
  FactoryBot.create(:fact_value, fact_name: fact_names['virt::uuid'], value: '1234', host: @host2)
258
260
 
@@ -261,4 +263,12 @@ class InventoryFullSyncTest < ActiveSupport::TestCase
261
263
 
262
264
  assert_equal InventorySync::InventoryStatus::DISCONNECT, InventorySync::InventoryStatus.where(host_id: @host1.id).first.status
263
265
  end
266
+
267
+ test 'Task should be aborted if token is not present' do
268
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: '')
269
+
270
+ InventorySync::Async::InventoryFullSync.any_instance.expects(:plan_self).never
271
+
272
+ ForemanTasks.sync_task(InventorySync::Async::InventoryFullSync, @host1.organization)
273
+ end
264
274
  end
@@ -6,6 +6,7 @@ class InventoryHostsSyncTest < ActiveSupport::TestCase
6
6
 
7
7
  setup do
8
8
  User.current = User.find_by(login: 'secret_admin')
9
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'MOCK_TOKEN')
9
10
 
10
11
  env = FactoryBot.create(:katello_k_t_environment)
11
12
  cv = env.content_views << FactoryBot.create(:katello_content_view, organization: env.organization)
@@ -6,6 +6,7 @@ class InventorySelfHostSyncTest < ActiveSupport::TestCase
6
6
 
7
7
  setup do
8
8
  User.current = User.find_by(login: 'secret_admin')
9
+ FactoryBot.create(:setting, name: 'rh_cloud_token', value: 'MOCK_TOKEN')
9
10
 
10
11
  # this host would pass our plugin queries, so it could be uploaded to the cloud.
11
12
  @host1 = FactoryBot.create(:host)
@@ -38,3 +38,56 @@ module KatelloLocationFix
38
38
  end
39
39
  end
40
40
  end
41
+
42
+ module MockCerts
43
+ extend ActiveSupport::Concern
44
+
45
+ def test_certificate
46
+ @test_certificate ||= "-----BEGIN CERTIFICATE-----\r\n" +
47
+ "MIIFdDCCA1ygAwIBAgIJAM5Uqykb3EAtMA0GCSqGSIb3DQEBCwUAME8xCzAJBgNV\r\n" +
48
+ "BAYTAklMMREwDwYDVQQIDAhUZWwgQXZpdjEUMBIGA1UECgwLVGhlIEZvcmVtYW4x\r\n" +
49
+ "FzAVBgNVBAMMDnRoZWZvcmVtYW4ub3JnMB4XDTE4MDMyNDEyMzYyOFoXDTI4MDMy\r\n" +
50
+ "MTEyMzYyOFowTzELMAkGA1UEBhMCSUwxETAPBgNVBAgMCFRlbCBBdml2MRQwEgYD\r\n" +
51
+ "VQQKDAtUaGUgRm9yZW1hbjEXMBUGA1UEAwwOdGhlZm9yZW1hbi5vcmcwggIiMA0G\r\n" +
52
+ "CSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDF04/s4h+BgHPG1HDZ/sDlYq925pkc\r\n" +
53
+ "RTVAfnE2EXDAmZ6W4Q9ueDY65MHe3ZWO5Dg72kNSP2sK9kRI7Dk5CAFOgyw1rH8t\r\n" +
54
+ "Hd1+0xp/lv6e4SvSYghxIL68vFe0ftKkm1usqejBM5ZTgKr7JCI+XSIN36F65Kde\r\n" +
55
+ "c+vxwBnayuhP04r9/aaE/709SXML4eRVYW8I3qFy9FPtUOm+bY8U2PIv5fHayqbG\r\n" +
56
+ "cL/4t3+MCtMhHJsLzdBXya+1P5t+HcKjUNlmwoUF961YAktVuEFloGd0RMRlqF3/\r\n" +
57
+ "itU3QNlXgA5QBIciE5VPr/PiqgMC3zgd5avjF4OribZ+N9AATLiQMW78il5wSfcc\r\n" +
58
+ "kQjU9ChOLrzku455vQ8KE4bc0qvpCWGfUah6MvL9JB+TQkRl/8kxl0b9ZinIvJDH\r\n" +
59
+ "ynVMb4cB/TDEjrjOfzn9mWLH0ZJqjmc2bER/G12WQxOaYLxdVwRStD3Yh6PtiFWu\r\n" +
60
+ "sXOk19UOTVkeuvGFVtvzLfEwQ1lDEo7+VBQz8FG/HBu2Hpq3IwCFrHuicikwjQJk\r\n" +
61
+ "nfturgD0rBOKEc1qWNZRCvovYOLL6ihvv5Orujsx5ZCHOAtnVNxkvIlFt2RS45LF\r\n" +
62
+ "MtPJyhAc6SjitllfUEirxprsbmeSZqrIfzcGaEhgOSnyik1WMv6bYiqPfBg8Fzjh\r\n" +
63
+ "vOCbtiDNPmvgOwIDAQABo1MwUTAdBgNVHQ4EFgQUtkAgQopsTtG9zSG3MgW2IxHD\r\n" +
64
+ "MDwwHwYDVR0jBBgwFoAUtkAgQopsTtG9zSG3MgW2IxHDMDwwDwYDVR0TAQH/BAUw\r\n" +
65
+ "AwEB/zANBgkqhkiG9w0BAQsFAAOCAgEAJq7iN+ZroRBweNhvUobxs75bLIV6tNn1\r\n" +
66
+ "MdNHDRA+hezwf+gxHZhFyaAHfTpst2/9leK5Qe5Zd6gZLr3E5/8ppQuRod72H39B\r\n" +
67
+ "vxMlG5zxDss0WMo3vZeKZbTY6QhXi/lY2IZ6OGV4feSvCsYxn27GTjjrRUSLFeHH\r\n" +
68
+ "JVemCwCDMavaE3+OIY4v2P4FcG+MjUvfOB9ahI24TWL7YgrsNVmJjCILq+EeUj0t\r\n" +
69
+ "Gde1SXVyLkqt7PoxHRJAE0BCEMJSnjxaVB329acJgeehBUxjj4CCPqtDxtbz9HEH\r\n" +
70
+ "mOKfNdaKpFor+DUeEKUWVGnr9U9xOaC+Ws+oX7MIEUCDM7p2ob4JwcjnFs1jZgHh\r\n" +
71
+ "Hwig+i7doTlc701PvKWO96fuNHK3B3/jTb1fVvSZ49O/RvY1VWODdUdxWmXGHNh3\r\n" +
72
+ "LoR8tSPEb46lC2DXGaIQumqQt8PnBG+vL1qkQa1SGTV7dJ8TTbxbv0S+sS+igkk9\r\n" +
73
+ "zsIEK8Ea3Ep935cXximz0faAAKHSA+It+xHLAyDtqy2KaAEBgGsBuuWlUfK6TaP3\r\n" +
74
+ "Gwdjct3y4yYUO45lUsUfHqX8vk/4ttW5zYeDiW+HArJz+9VUXNbEdury4kGuHgBj\r\n" +
75
+ "xHD4Bsul65+hHZ9QywKU26F1A6TLkYpQ2rk/Dx9LGICM4m4IlHjWJPFsQdtkyOor\r\n" +
76
+ "osxMtcaZZ1E=\r\n" +
77
+ "-----END CERTIFICATE-----"
78
+ end
79
+
80
+ def generate_certs_hash
81
+ {
82
+ cert: test_certificate,
83
+ key: OpenSSL::PKey::RSA.new(1024).to_pem,
84
+ }
85
+ end
86
+
87
+ def setup_certs_expectation
88
+ expectation = yield
89
+ expectation.returns(
90
+ generate_certs_hash
91
+ )
92
+ end
93
+ end
@@ -0,0 +1,28 @@
1
+ require 'test_plugin_helper'
2
+
3
+ class ForemanRhCloudSelfHostTest < ActiveSupport::TestCase
4
+ setup do
5
+ # reset cached value
6
+ ForemanRhCloud.instance_variable_set(:@foreman_host, nil)
7
+ end
8
+
9
+ test 'finds host by fullname' do
10
+ @domain
11
+ @host = FactoryBot.create(:host, :managed)
12
+ ForemanRhCloud.expects(:foreman_host_name).returns(@host.name)
13
+
14
+ actual = ForemanRhCloud.foreman_host
15
+
16
+ assert_not_nil actual
17
+ end
18
+
19
+ test 'finds host by shortname' do
20
+ @host = FactoryBot.create(:host, :managed)
21
+ Host.where(name: @host.name).update_all(name: @host.shortname)
22
+ ForemanRhCloud.expects(:foreman_host_name).returns(@host.name)
23
+
24
+ actual = ForemanRhCloud.foreman_host
25
+
26
+ assert_not_nil actual
27
+ end
28
+ end