foreman_rh_cloud 13.0.8 → 13.0.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (130) hide show
  1. checksums.yaml +4 -4
  2. data/app/controllers/concerns/inventory_upload/report_actions.rb +8 -1
  3. data/app/controllers/foreman_inventory_upload/accounts_controller.rb +82 -7
  4. data/app/controllers/foreman_inventory_upload/api/tasks_controller.rb +110 -0
  5. data/app/controllers/foreman_inventory_upload/reports_controller.rb +41 -17
  6. data/app/controllers/foreman_inventory_upload/uploads_controller.rb +0 -9
  7. data/config/routes.rb +4 -2
  8. data/db/migrate/20251209163012_drop_task_output_tables.foreman_rh_cloud.rb +24 -0
  9. data/lib/foreman_inventory_upload/async/generate_all_reports_job.rb +1 -1
  10. data/lib/foreman_inventory_upload/async/host_inventory_report_job.rb +39 -0
  11. data/lib/foreman_inventory_upload/async/queue_for_upload_job.rb +1 -23
  12. data/lib/foreman_inventory_upload/async/upload_report_direct_job.rb +171 -0
  13. data/lib/foreman_inventory_upload.rb +0 -4
  14. data/lib/foreman_rh_cloud/plugin.rb +1 -0
  15. data/lib/foreman_rh_cloud/version.rb +1 -1
  16. data/lib/inventory_sync/async/inventory_hosts_sync.rb +0 -2
  17. data/lib/tasks/rh_cloud_inventory.rake +4 -2
  18. data/package.json +1 -1
  19. data/test/controllers/accounts_controller_test.rb +10 -11
  20. data/test/controllers/insights_cloud/api/cloud_request_controller_test.rb +1 -2
  21. data/test/jobs/host_inventory_report_job_test.rb +161 -97
  22. data/test/jobs/queue_for_upload_job_test.rb +1 -12
  23. data/test/jobs/single_host_report_job_test.rb +36 -54
  24. data/test/jobs/upload_report_direct_job_test.rb +399 -0
  25. data/test/unit/rh_cloud_permissions_test.rb +2 -0
  26. data/webpack/ForemanInventoryUpload/Components/AccountList/AccountList.fixtures.js +6 -6
  27. data/webpack/ForemanInventoryUpload/Components/AccountList/AccountList.js +49 -34
  28. data/webpack/ForemanInventoryUpload/Components/AccountList/AccountListActions.js +2 -2
  29. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItem/ListItem.fixtures.js +4 -5
  30. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItem/ListItem.js +15 -7
  31. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItem/__tests__/__snapshots__/ListItem.test.js.snap +11 -11
  32. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItemStatus/ListItemStatus.fixtures.js +2 -2
  33. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItemStatus/ListItemStatus.js +10 -14
  34. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItemStatus/ListItemStatusHelper.js +9 -4
  35. data/webpack/ForemanInventoryUpload/Components/AccountList/Components/ListItemStatus/__tests__/__snapshots__/ListItemStatus.test.js.snap +4 -4
  36. data/webpack/ForemanInventoryUpload/Components/AccountList/__tests__/__snapshots__/AccountList.test.js.snap +15 -9
  37. data/webpack/ForemanInventoryUpload/Components/AccountList/__tests__/__snapshots__/AccountListActions.test.js.snap +7 -7
  38. data/webpack/ForemanInventoryUpload/Components/AccountList/__tests__/__snapshots__/AccountListReducer.test.js.snap +6 -6
  39. data/webpack/ForemanInventoryUpload/Components/AccountList/__tests__/__snapshots__/AccountListSelectors.test.js.snap +12 -12
  40. data/webpack/ForemanInventoryUpload/Components/Dashboard/Dashboard.js +37 -130
  41. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/Dashboard.test.js +60 -17
  42. data/webpack/ForemanInventoryUpload/Components/Dashboard/index.js +1 -34
  43. data/webpack/ForemanInventoryUpload/Components/InventoryFilter/__tests__/__snapshots__/integration.test.js.snap +0 -1
  44. data/webpack/ForemanInventoryUpload/Components/NavContainer/NavContainer.js +1 -26
  45. data/webpack/ForemanInventoryUpload/Components/PageHeader/PageHeader.js +24 -17
  46. data/webpack/ForemanInventoryUpload/Components/PageHeader/__tests__/PageHeader.test.js +178 -8
  47. data/webpack/ForemanInventoryUpload/Components/PageHeader/__tests__/__snapshots__/PageTitle.test.js.snap +2 -2
  48. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/ToolbarButtons/ToolbarButtons.js +3 -1
  49. data/webpack/ForemanInventoryUpload/Components/PageHeader/components/ToolbarButtons/__tests__/ToolbarButtons.test.js +69 -51
  50. data/webpack/ForemanInventoryUpload/Components/TabHeader/TabHeader.js +22 -9
  51. data/webpack/ForemanInventoryUpload/Components/TabHeader/__tests__/TabHeader.test.js +67 -4
  52. data/webpack/ForemanInventoryUpload/Components/TaskHistory/TaskHistory.js +140 -0
  53. data/webpack/ForemanInventoryUpload/Components/TaskHistory/index.js +1 -0
  54. data/webpack/ForemanInventoryUpload/Components/TaskHistory/taskHistory.scss +40 -0
  55. data/webpack/ForemanInventoryUpload/Components/TaskProgress/TaskProgress.js +340 -0
  56. data/webpack/ForemanInventoryUpload/Components/TaskProgress/index.js +1 -0
  57. data/webpack/ForemanInventoryUpload/Components/TaskProgress/taskProgress.scss +8 -0
  58. data/webpack/ForemanInventoryUpload/ForemanInventoryHelpers.js +2 -2
  59. data/webpack/ForemanInventoryUpload/ForemanInventoryUploadReducers.js +0 -2
  60. data/webpack/ForemanInventoryUpload/__tests__/__snapshots__/ForemanInventoryHelpers.test.js.snap +1 -1
  61. data/webpack/ForemanRhCloudPages.js +0 -1
  62. data/webpack/InsightsCloudSync/Components/InsightsTable/__tests__/InsightsTable.test.js +11 -19
  63. data/webpack/InsightsCloudSync/Components/RemediationModal/RemediationHelpers.js +1 -2
  64. data/webpack/InsightsCloudSync/Components/RemediationModal/RemediationModal.js +2 -4
  65. data/webpack/InsightsVulnerabilityHostIndexExtensions/__tests__/CVECountCell.test.js +77 -22
  66. data/webpack/__mocks__/foremanReact/components/common/dates/RelativeDateTime.js +14 -0
  67. data/webpack/__tests__/ForemanRhCloudHelpers.test.js +5 -1
  68. metadata +13 -68
  69. data/app/models/task_output_line.rb +0 -2
  70. data/app/models/task_output_status.rb +0 -2
  71. data/lib/foreman_inventory_upload/async/generate_report_job.rb +0 -61
  72. data/lib/foreman_inventory_upload/async/progress_output.rb +0 -38
  73. data/lib/foreman_inventory_upload/async/shell_process.rb +0 -77
  74. data/lib/foreman_inventory_upload/async/upload_report_job.rb +0 -97
  75. data/lib/foreman_inventory_upload/scripts/uploader.sh.erb +0 -55
  76. data/test/controllers/reports_controller_test.rb +0 -21
  77. data/test/controllers/uploads_controller_test.rb +0 -21
  78. data/test/jobs/generate_report_job_test.rb +0 -146
  79. data/test/jobs/upload_report_job_test.rb +0 -38
  80. data/test/unit/shell_process_job_test.rb +0 -29
  81. data/webpack/ForemanInventoryUpload/Components/Dashboard/DashboardActions.js +0 -88
  82. data/webpack/ForemanInventoryUpload/Components/Dashboard/DashboardConstants.js +0 -9
  83. data/webpack/ForemanInventoryUpload/Components/Dashboard/DashboardReducer.js +0 -68
  84. data/webpack/ForemanInventoryUpload/Components/Dashboard/DashboardSelectors.js +0 -17
  85. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/DashboardActions.test.js +0 -51
  86. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/DashboardIntegration.test.js +0 -17
  87. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/DashboardReducer.test.js +0 -64
  88. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/DashboardSelectors.test.js +0 -46
  89. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/__snapshots__/Dashboard.test.js.snap +0 -36
  90. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/__snapshots__/DashboardActions.test.js.snap +0 -76
  91. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/__snapshots__/DashboardReducer.test.js.snap +0 -44
  92. data/webpack/ForemanInventoryUpload/Components/Dashboard/__tests__/__snapshots__/DashboardSelectors.test.js.snap +0 -42
  93. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/FullScreenModal.fixtures.js +0 -0
  94. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/FullScreenModal.js +0 -55
  95. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/FullScreenModalHelper.js +0 -0
  96. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/__tests__/FullScreenModal.test.js +0 -13
  97. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/__tests__/__snapshots__/FullScreenModal.test.js.snap +0 -65
  98. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/fullScreenModal.scss +0 -20
  99. data/webpack/ForemanInventoryUpload/Components/FullScreenModal/index.js +0 -1
  100. data/webpack/ForemanInventoryUpload/Components/PageHeader/__tests__/__snapshots__/PageHeader.test.js.snap +0 -36
  101. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/ReportGenerate.fixtures.js +0 -18
  102. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/ReportGenerate.js +0 -65
  103. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/ReportGenerateHelper.js +0 -0
  104. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/__tests__/ReportGenerate.test.js +0 -14
  105. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/__tests__/__snapshots__/ReportGenerate.test.js.snap +0 -47
  106. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/index.js +0 -1
  107. data/webpack/ForemanInventoryUpload/Components/ReportGenerate/reportGenerate.scss +0 -0
  108. data/webpack/ForemanInventoryUpload/Components/ReportUpload/ReportUpload.fixtures.js +0 -18
  109. data/webpack/ForemanInventoryUpload/Components/ReportUpload/ReportUpload.js +0 -46
  110. data/webpack/ForemanInventoryUpload/Components/ReportUpload/ReportUploadHelper.js +0 -0
  111. data/webpack/ForemanInventoryUpload/Components/ReportUpload/__tests__/ReportUpload.test.js +0 -14
  112. data/webpack/ForemanInventoryUpload/Components/ReportUpload/__tests__/__snapshots__/ReportUpload.test.js.snap +0 -47
  113. data/webpack/ForemanInventoryUpload/Components/ReportUpload/index.js +0 -1
  114. data/webpack/ForemanInventoryUpload/Components/ReportUpload/reportUpload.scss +0 -0
  115. data/webpack/ForemanInventoryUpload/Components/TabBody/TabBody.fixtures.js +0 -0
  116. data/webpack/ForemanInventoryUpload/Components/TabBody/TabBody.js +0 -31
  117. data/webpack/ForemanInventoryUpload/Components/TabBody/TabBodyHelper.js +0 -0
  118. data/webpack/ForemanInventoryUpload/Components/TabBody/__tests__/TabBody.test.js +0 -13
  119. data/webpack/ForemanInventoryUpload/Components/TabBody/__tests__/__snapshots__/TabBody.test.js.snap +0 -19
  120. data/webpack/ForemanInventoryUpload/Components/TabBody/index.js +0 -1
  121. data/webpack/ForemanInventoryUpload/Components/TabBody/tabBody.scss +0 -5
  122. data/webpack/ForemanInventoryUpload/Components/Terminal/Terminal.fixtures.js +0 -10
  123. data/webpack/ForemanInventoryUpload/Components/Terminal/Terminal.js +0 -110
  124. data/webpack/ForemanInventoryUpload/Components/Terminal/TerminalHelper.js +0 -6
  125. data/webpack/ForemanInventoryUpload/Components/Terminal/__tests__/Terminal.test.js +0 -34
  126. data/webpack/ForemanInventoryUpload/Components/Terminal/__tests__/__snapshots__/Terminal.test.js.snap +0 -98
  127. data/webpack/ForemanInventoryUpload/Components/Terminal/index.js +0 -1
  128. data/webpack/ForemanInventoryUpload/Components/Terminal/terminal.scss +0 -32
  129. data/webpack/InsightsCloudSync/Components/InsightsTable/__tests__/__snapshots__/InsightsTable.test.js.snap +0 -112
  130. data/webpack/__mocks__/foremanReact/common/hooks/API/APIHooks.js +0 -3
@@ -1,3 +1,3 @@
1
1
  module ForemanRhCloud
2
- VERSION = '13.0.8'.freeze
2
+ VERSION = '13.0.10'.freeze
3
3
  end
@@ -8,8 +8,6 @@ module InventorySync
8
8
  set_callback :step, :around, :create_missing_hosts
9
9
 
10
10
  def plan(organizations)
11
- # Do not run for local advisor, since we use sub-man id to identify hosts.
12
- return if ForemanRhCloud.with_iop_smart_proxy?
13
11
  # by default the tasks will be executed concurrently
14
12
  super(organizations)
15
13
  plan_self_host_sync
@@ -12,9 +12,11 @@ namespace :rh_cloud_inventory do
12
12
  User.as_anonymous_admin do
13
13
  organizations.each do |organization|
14
14
  ForemanTasks.async_task(
15
- ForemanInventoryUpload::Async::GenerateReportJob,
15
+ ForemanInventoryUpload::Async::HostInventoryReportJob,
16
16
  ForemanInventoryUpload.generated_reports_folder,
17
- organization.id
17
+ organization.id,
18
+ '', # hosts_filter
19
+ true # upload
18
20
  )
19
21
  puts "Generated and uploaded inventory report for organization '#{organization.name}'"
20
22
  end
data/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "foreman_rh_cloud",
3
- "version": "13.0.8",
3
+ "version": "13.0.10",
4
4
  "description": "Inventory Upload =============",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -5,22 +5,21 @@ class AccountsControllerTest < ActionController::TestCase
5
5
 
6
6
  include FolderIsolation
7
7
 
8
- test 'Returns statuses for each process type' do
8
+ test 'Returns statuses for each organization' do
9
9
  test_org = FactoryBot.create(:organization)
10
10
 
11
- generate_label = ForemanInventoryUpload::Async::GenerateReportJob.output_label(test_org.id)
12
- generate_output = ForemanInventoryUpload::Async::ProgressOutput.register(generate_label)
13
- generate_output.status = 'generate_status_test'
14
- upload_label = ForemanInventoryUpload::Async::UploadReportJob.output_label(test_org.id)
15
- upload_output = ForemanInventoryUpload::Async::ProgressOutput.register(upload_label)
16
- upload_output.status = 'upload_status_test'
17
-
18
11
  get :index, session: set_session_user
19
12
 
20
13
  assert_response :success
21
14
  actual = JSON.parse(response.body)
22
- actual_account_statuses = actual['accounts'][test_org.label]
23
- assert_equal 'generate_status_test', actual_account_statuses['generate_report_status']
24
- assert_equal 'upload_status_test', actual_account_statuses['upload_report_status']
15
+ assert actual['accounts'].key?(test_org.name)
16
+ actual_account = actual['accounts'][test_org.name]
17
+
18
+ # Verify the response structure
19
+ assert_includes actual_account.keys, 'generated_status'
20
+ assert_includes actual_account.keys, 'uploaded_status'
21
+ assert_includes actual_account.keys, 'generate_task'
22
+ assert_includes actual_account.keys, 'report_file_paths'
23
+ assert_equal test_org.id, actual_account['id']
25
24
  end
26
25
  end
@@ -29,8 +29,7 @@ module InsightsCloud::Api
29
29
  mock_composer = mock('composer')
30
30
  ::JobInvocationComposer.expects(:for_feature).with do |feature, host_ids, params|
31
31
  feature == :rh_cloud_connector_run_playbook &&
32
- host_ids.first == host1.id &&
33
- host_ids.last == host2.id
32
+ host_ids.sort == [host1.id, host2.id].sort
34
33
  end.returns(mock_composer)
35
34
  mock_composer.expects(:trigger!)
36
35
  mock_composer.expects(:job_invocation)
@@ -15,13 +15,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
15
15
  end
16
16
 
17
17
  test 'plan schedules GenerateHostReport action' do
18
- action = create_and_plan_action(
19
- ForemanInventoryUpload::Async::HostInventoryReportJob,
20
- base_folder,
21
- organization.id,
22
- hosts_filter,
23
- upload
24
- )
18
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
19
+ action.expects(:action_subject).with(organization)
20
+ plan_action(action, base_folder, organization.id, hosts_filter, upload)
25
21
 
26
22
  assert_action_planned_with(
27
23
  action,
@@ -35,13 +31,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
35
31
  test 'plan schedules QueueForUploadJob when upload is true' do
36
32
  expected_archive_name = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
37
33
 
38
- action = create_and_plan_action(
39
- ForemanInventoryUpload::Async::HostInventoryReportJob,
40
- base_folder,
41
- organization.id,
42
- hosts_filter,
43
- true
44
- )
34
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
35
+ action.expects(:action_subject).with(organization)
36
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
45
37
 
46
38
  assert_action_planned_with(
47
39
  action,
@@ -53,24 +45,17 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
53
45
  end
54
46
 
55
47
  test 'plan skips QueueForUploadJob when upload is false' do
56
- action = create_and_plan_action(
57
- ForemanInventoryUpload::Async::HostInventoryReportJob,
58
- base_folder,
59
- organization.id,
60
- hosts_filter,
61
- false
62
- )
48
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
49
+ action.expects(:action_subject).with(organization)
50
+ plan_action(action, base_folder, organization.id, hosts_filter, false)
63
51
 
64
52
  refute_action_planned(action, ForemanInventoryUpload::Async::QueueForUploadJob)
65
53
  end
66
54
 
67
55
  test 'plan defaults upload to true when not specified' do
68
- action = create_and_plan_action(
69
- ForemanInventoryUpload::Async::HostInventoryReportJob,
70
- base_folder,
71
- organization.id,
72
- hosts_filter
73
- )
56
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
57
+ action.expects(:action_subject).with(organization)
58
+ plan_action(action, base_folder, organization.id, hosts_filter)
74
59
 
75
60
  assert_action_planned(action, ForemanInventoryUpload::Async::QueueForUploadJob)
76
61
  end
@@ -78,13 +63,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
78
63
  test 'plan schedules CreateMissingInsightsFacets when IoP is enabled' do
79
64
  ForemanRhCloud.stubs(:with_iop_smart_proxy?).returns(true)
80
65
 
81
- action = create_and_plan_action(
82
- ForemanInventoryUpload::Async::HostInventoryReportJob,
83
- base_folder,
84
- organization.id,
85
- hosts_filter,
86
- upload
87
- )
66
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
67
+ action.expects(:action_subject).with(organization)
68
+ plan_action(action, base_folder, organization.id, hosts_filter, upload)
88
69
 
89
70
  assert_action_planned_with(
90
71
  action,
@@ -96,13 +77,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
96
77
  test 'plan skips CreateMissingInsightsFacets when IoP is disabled' do
97
78
  ForemanRhCloud.stubs(:with_iop_smart_proxy?).returns(false)
98
79
 
99
- action = create_and_plan_action(
100
- ForemanInventoryUpload::Async::HostInventoryReportJob,
101
- base_folder,
102
- organization.id,
103
- hosts_filter,
104
- upload
105
- )
80
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
81
+ action.expects(:action_subject).with(organization)
82
+ plan_action(action, base_folder, organization.id, hosts_filter, upload)
106
83
 
107
84
  refute_action_planned(action, ForemanInventoryUpload::Async::CreateMissingInsightsFacets)
108
85
  end
@@ -110,13 +87,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
110
87
  test 'plan schedules all three actions with IoP enabled and upload true' do
111
88
  ForemanRhCloud.stubs(:with_iop_smart_proxy?).returns(true)
112
89
 
113
- action = create_and_plan_action(
114
- ForemanInventoryUpload::Async::HostInventoryReportJob,
115
- base_folder,
116
- organization.id,
117
- hosts_filter,
118
- true
119
- )
90
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
91
+ action.expects(:action_subject).with(organization)
92
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
120
93
 
121
94
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
122
95
  assert_action_planned(action, ForemanInventoryUpload::Async::QueueForUploadJob)
@@ -126,13 +99,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
126
99
  test 'plan schedules only generation and facets with IoP enabled and upload false' do
127
100
  ForemanRhCloud.stubs(:with_iop_smart_proxy?).returns(true)
128
101
 
129
- action = create_and_plan_action(
130
- ForemanInventoryUpload::Async::HostInventoryReportJob,
131
- base_folder,
132
- organization.id,
133
- hosts_filter,
134
- false
135
- )
102
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
103
+ action.expects(:action_subject).with(organization)
104
+ plan_action(action, base_folder, organization.id, hosts_filter, false)
136
105
 
137
106
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
138
107
  refute_action_planned(action, ForemanInventoryUpload::Async::QueueForUploadJob)
@@ -140,25 +109,17 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
140
109
  end
141
110
 
142
111
  test 'humanized_name returns correct string' do
143
- action = create_and_plan_action(
144
- ForemanInventoryUpload::Async::HostInventoryReportJob,
145
- base_folder,
146
- organization.id,
147
- hosts_filter,
148
- upload
149
- )
112
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
113
+ action.expects(:action_subject).with(organization)
114
+ plan_action(action, base_folder, organization.id, hosts_filter, upload)
150
115
 
151
116
  assert_equal 'Host inventory report job', action.humanized_name
152
117
  end
153
118
 
154
119
  test 'handles empty hosts_filter parameter' do
155
- action = create_and_plan_action(
156
- ForemanInventoryUpload::Async::HostInventoryReportJob,
157
- base_folder,
158
- organization.id,
159
- '',
160
- upload
161
- )
120
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
121
+ action.expects(:action_subject).with(organization)
122
+ plan_action(action, base_folder, organization.id, '', upload)
162
123
 
163
124
  assert_action_planned_with(
164
125
  action,
@@ -173,13 +134,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
173
134
  custom_filter = 'name~production'
174
135
  expected_archive_name = ForemanInventoryUpload.facts_archive_name(organization.id, custom_filter)
175
136
 
176
- action = create_and_plan_action(
177
- ForemanInventoryUpload::Async::HostInventoryReportJob,
178
- base_folder,
179
- organization.id,
180
- custom_filter,
181
- upload
182
- )
137
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
138
+ action.expects(:action_subject).with(organization)
139
+ plan_action(action, base_folder, organization.id, custom_filter, upload)
183
140
 
184
141
  assert_action_planned_with(
185
142
  action,
@@ -200,13 +157,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
200
157
  test 'handles invalid hosts_filter parameter' do
201
158
  invalid_filter = 'name~~'
202
159
 
203
- action = create_and_plan_action(
204
- ForemanInventoryUpload::Async::HostInventoryReportJob,
205
- base_folder,
206
- organization.id,
207
- invalid_filter,
208
- upload
209
- )
160
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
161
+ action.expects(:action_subject).with(organization)
162
+ plan_action(action, base_folder, organization.id, invalid_filter, upload)
210
163
 
211
164
  # Job should still plan even with invalid filter syntax
212
165
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
@@ -215,13 +168,9 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
215
168
  test 'handles potentially malicious hosts_filter parameter' do
216
169
  malicious_filter = "'; DROP TABLE hosts; --"
217
170
 
218
- action = create_and_plan_action(
219
- ForemanInventoryUpload::Async::HostInventoryReportJob,
220
- base_folder,
221
- organization.id,
222
- malicious_filter,
223
- upload
224
- )
171
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
172
+ action.expects(:action_subject).with(organization)
173
+ plan_action(action, base_folder, organization.id, malicious_filter, upload)
225
174
 
226
175
  # Job should handle malicious input safely (filter is parameterized)
227
176
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
@@ -230,15 +179,130 @@ class HostInventoryReportJobTest < ActiveSupport::TestCase
230
179
  test 'handles non-matching hosts_filter parameter' do
231
180
  non_matching_filter = 'name~doesnotexist'
232
181
 
233
- action = create_and_plan_action(
234
- ForemanInventoryUpload::Async::HostInventoryReportJob,
235
- base_folder,
236
- organization.id,
237
- non_matching_filter,
238
- upload
239
- )
182
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
183
+ action.expects(:action_subject).with(organization)
184
+ plan_action(action, base_folder, organization.id, non_matching_filter, upload)
240
185
 
241
186
  # Job should plan successfully even if filter matches no hosts
242
187
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
243
188
  end
189
+
190
+ test 'organization returns correct Organization from input' do
191
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
192
+ action.expects(:action_subject).with(organization)
193
+ plan_action(action, base_folder, organization.id, hosts_filter, upload)
194
+
195
+ assert_equal organization.id, action.organization.id
196
+ assert_instance_of Organization, action.organization
197
+ end
198
+
199
+ test 'resource_locks returns :link' do
200
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
201
+
202
+ assert_equal :link, action.resource_locks
203
+ end
204
+
205
+ test 'report_file_path returns nil when no file exists' do
206
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
207
+ action.expects(:action_subject).with(organization)
208
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
209
+
210
+ assert_nil action.report_file_path
211
+ end
212
+
213
+ test 'report_file_path finds file in done folder for upload tasks' do
214
+ filename = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
215
+ done_path = ForemanInventoryUpload.done_file_path(filename)
216
+
217
+ # Create the done file
218
+ FileUtils.mkdir_p(File.dirname(done_path))
219
+ FileUtils.touch(done_path)
220
+
221
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
222
+ action.expects(:action_subject).with(organization)
223
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
224
+
225
+ assert_equal done_path, action.report_file_path
226
+
227
+ # Cleanup
228
+ FileUtils.rm_f(done_path)
229
+ end
230
+
231
+ test 'report_file_path finds file in uploads folder for upload tasks' do
232
+ filename = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
233
+ uploads_path = ForemanInventoryUpload.uploads_file_path(filename)
234
+
235
+ # Create the uploads file
236
+ FileUtils.mkdir_p(File.dirname(uploads_path))
237
+ FileUtils.touch(uploads_path)
238
+
239
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
240
+ action.expects(:action_subject).with(organization)
241
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
242
+
243
+ assert_equal uploads_path, action.report_file_path
244
+
245
+ # Cleanup
246
+ FileUtils.rm_f(uploads_path)
247
+ end
248
+
249
+ test 'report_file_path finds file in generated_reports folder for upload tasks' do
250
+ filename = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
251
+ generated_path = File.join(base_folder, filename)
252
+
253
+ # Create the generated file
254
+ FileUtils.mkdir_p(base_folder)
255
+ FileUtils.touch(generated_path)
256
+
257
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
258
+ action.expects(:action_subject).with(organization)
259
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
260
+
261
+ assert_equal generated_path, action.report_file_path
262
+ end
263
+
264
+ test 'report_file_path only checks generated_reports folder for non-upload tasks' do
265
+ filename = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
266
+ generated_path = File.join(base_folder, filename)
267
+ done_path = ForemanInventoryUpload.done_file_path(filename)
268
+
269
+ # Create files in both locations
270
+ FileUtils.mkdir_p(base_folder)
271
+ FileUtils.touch(generated_path)
272
+ FileUtils.mkdir_p(File.dirname(done_path))
273
+ FileUtils.touch(done_path)
274
+
275
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
276
+ action.expects(:action_subject).with(organization)
277
+ plan_action(action, base_folder, organization.id, hosts_filter, false)
278
+
279
+ # Should return the generated_path, not the done_path (since upload=false)
280
+ assert_equal generated_path, action.report_file_path
281
+
282
+ # Cleanup
283
+ FileUtils.rm_f(done_path)
284
+ end
285
+
286
+ test 'report_file_path prioritizes done folder over uploads folder' do
287
+ filename = ForemanInventoryUpload.facts_archive_name(organization.id, hosts_filter)
288
+ done_path = ForemanInventoryUpload.done_file_path(filename)
289
+ uploads_path = ForemanInventoryUpload.uploads_file_path(filename)
290
+
291
+ # Create files in both locations
292
+ FileUtils.mkdir_p(File.dirname(done_path))
293
+ FileUtils.touch(done_path)
294
+ FileUtils.mkdir_p(File.dirname(uploads_path))
295
+ FileUtils.touch(uploads_path)
296
+
297
+ action = create_action(ForemanInventoryUpload::Async::HostInventoryReportJob)
298
+ action.expects(:action_subject).with(organization)
299
+ plan_action(action, base_folder, organization.id, hosts_filter, true)
300
+
301
+ # Should prefer done_path (uploaded) over uploads_path (queued)
302
+ assert_equal done_path, action.report_file_path
303
+
304
+ # Cleanup
305
+ FileUtils.rm_f(done_path)
306
+ FileUtils.rm_f(uploads_path)
307
+ end
244
308
  end
@@ -11,13 +11,6 @@ class QueueForUploadJobTest < ActiveSupport::TestCase
11
11
  let(:uploads_folder) { ForemanInventoryUpload.uploads_folder }
12
12
 
13
13
  setup do
14
- # Stub the script template source
15
- script_source = File.join(ForemanRhCloud::Engine.root, 'lib/foreman_inventory_upload/scripts/uploader.sh.erb')
16
- File.stubs(:read).with(script_source).returns('#!/bin/bash\necho "Test script"')
17
-
18
- # Stub template rendering
19
- Foreman::Renderer.stubs(:render).returns('#!/bin/bash\necho "Rendered script"')
20
-
21
14
  # Stub additional settings that are accessed
22
15
  Setting.stubs(:[]).with(:content_default_http_proxy).returns(nil)
23
16
  Setting.stubs(:[]).with(:http_proxy).returns(nil)
@@ -49,7 +42,7 @@ class QueueForUploadJobTest < ActiveSupport::TestCase
49
42
  assert File.exist?(File.join(uploads_folder, report_file)), "File should exist in uploads folder"
50
43
  end
51
44
 
52
- test 'creates necessary folders and scripts' do
45
+ test 'creates necessary folders' do
53
46
  ForemanInventoryUpload::Async::QueueForUploadJob.any_instance.stubs(:plan_upload_report)
54
47
 
55
48
  action = create_and_plan_action(ForemanInventoryUpload::Async::QueueForUploadJob, base_folder, report_file, organization.id)
@@ -57,9 +50,5 @@ class QueueForUploadJobTest < ActiveSupport::TestCase
57
50
 
58
51
  # Verify the uploads folder was created
59
52
  assert Dir.exist?(uploads_folder), "Uploads folder should be created"
60
-
61
- # Verify the script file was created
62
- script_path = File.join(uploads_folder, ForemanInventoryUpload.upload_script_file)
63
- assert File.exist?(script_path), "Upload script should be created"
64
53
  end
65
54
  end
@@ -28,12 +28,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
28
28
  end
29
29
 
30
30
  test 'plan sets host_id in input' do
31
- action = create_and_plan_action(
32
- ForemanInventoryUpload::Async::SingleHostReportJob,
33
- base_folder,
34
- @host.organization_id,
35
- @host.id
36
- )
31
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
32
+ organization = Organization.find(@host.organization_id)
33
+ action.expects(:action_subject).with(organization)
34
+ plan_action(action, base_folder, @host.organization_id, @host.id)
37
35
 
38
36
  assert_equal @host.id, action.input[:host_id]
39
37
  end
@@ -41,12 +39,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
41
39
  test 'plan calls super with id filter' do
42
40
  expected_filter = "id=#{@host.id}"
43
41
 
44
- action = create_and_plan_action(
45
- ForemanInventoryUpload::Async::SingleHostReportJob,
46
- base_folder,
47
- @host.organization_id,
48
- @host.id
49
- )
42
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
43
+ organization = Organization.find(@host.organization_id)
44
+ action.expects(:action_subject).with(organization)
45
+ plan_action(action, base_folder, @host.organization_id, @host.id)
50
46
 
51
47
  assert_action_planned_with(
52
48
  action,
@@ -58,12 +54,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
58
54
  end
59
55
 
60
56
  test 'inherits behavior from HostInventoryReportJob' do
61
- action = create_and_plan_action(
62
- ForemanInventoryUpload::Async::SingleHostReportJob,
63
- base_folder,
64
- @host.organization_id,
65
- @host.id
66
- )
57
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
58
+ organization = Organization.find(@host.organization_id)
59
+ action.expects(:action_subject).with(organization)
60
+ plan_action(action, base_folder, @host.organization_id, @host.id)
67
61
 
68
62
  # Should schedule all parent actions
69
63
  assert_action_planned(action, ForemanInventoryUpload::Async::GenerateHostReport)
@@ -71,12 +65,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
71
65
  end
72
66
 
73
67
  test 'humanized_name includes hostname' do
74
- action = create_and_plan_action(
75
- ForemanInventoryUpload::Async::SingleHostReportJob,
76
- base_folder,
77
- @host.organization_id,
78
- @host.id
79
- )
68
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
69
+ organization = Organization.find(@host.organization_id)
70
+ action.expects(:action_subject).with(organization)
71
+ plan_action(action, base_folder, @host.organization_id, @host.id)
80
72
 
81
73
  assert_equal "Single-host report job for host #{@host.name}", action.humanized_name
82
74
  end
@@ -84,34 +76,28 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
84
76
  test 'humanized_name handles missing host' do
85
77
  non_existent_host_id = 999_999
86
78
 
87
- action = create_and_plan_action(
88
- ForemanInventoryUpload::Async::SingleHostReportJob,
89
- base_folder,
90
- @host.organization_id,
91
- non_existent_host_id
92
- )
79
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
80
+ organization = Organization.find(@host.organization_id)
81
+ action.expects(:action_subject).with(organization)
82
+ plan_action(action, base_folder, @host.organization_id, non_existent_host_id)
93
83
 
94
84
  assert_equal 'Single-host report job', action.humanized_name
95
85
  end
96
86
 
97
87
  test 'hostname method returns correct name' do
98
- action = create_and_plan_action(
99
- ForemanInventoryUpload::Async::SingleHostReportJob,
100
- base_folder,
101
- @host.organization_id,
102
- @host.id
103
- )
88
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
89
+ organization = Organization.find(@host.organization_id)
90
+ action.expects(:action_subject).with(organization)
91
+ plan_action(action, base_folder, @host.organization_id, @host.id)
104
92
 
105
93
  assert_equal @host.name, action.hostname(@host.id)
106
94
  end
107
95
 
108
96
  test 'hostname method handles nil gracefully' do
109
- action = create_and_plan_action(
110
- ForemanInventoryUpload::Async::SingleHostReportJob,
111
- base_folder,
112
- @host.organization_id,
113
- @host.id
114
- )
97
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
98
+ organization = Organization.find(@host.organization_id)
99
+ action.expects(:action_subject).with(organization)
100
+ plan_action(action, base_folder, @host.organization_id, @host.id)
115
101
 
116
102
  assert_nil action.hostname(999_999)
117
103
  end
@@ -120,12 +106,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
120
106
  expected_filter = "id=#{@host.id}"
121
107
  expected_archive_name = ForemanInventoryUpload.facts_archive_name(@host.organization_id, expected_filter)
122
108
 
123
- action = create_and_plan_action(
124
- ForemanInventoryUpload::Async::SingleHostReportJob,
125
- base_folder,
126
- @host.organization_id,
127
- @host.id
128
- )
109
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
110
+ organization = Organization.find(@host.organization_id)
111
+ action.expects(:action_subject).with(organization)
112
+ plan_action(action, base_folder, @host.organization_id, @host.id)
129
113
 
130
114
  assert_action_planned_with(
131
115
  action,
@@ -139,12 +123,10 @@ class SingleHostReportJobTest < ActiveSupport::TestCase
139
123
  test 'respects IoP mode for facet creation' do
140
124
  ForemanRhCloud.stubs(:with_iop_smart_proxy?).returns(true)
141
125
 
142
- action = create_and_plan_action(
143
- ForemanInventoryUpload::Async::SingleHostReportJob,
144
- base_folder,
145
- @host.organization_id,
146
- @host.id
147
- )
126
+ action = create_action(ForemanInventoryUpload::Async::SingleHostReportJob)
127
+ organization = Organization.find(@host.organization_id)
128
+ action.expects(:action_subject).with(organization)
129
+ plan_action(action, base_folder, @host.organization_id, @host.id)
148
130
 
149
131
  assert_action_planned_with(
150
132
  action,