Skip to content

Commit

Permalink
Fixes #36310 - Migrate off ContentViews generated for repository export
Browse files Browse the repository at this point in the history
Ensures no Hosts remain on ContentViews generated for repository export.
If doing so would leave the Host a valid ContentView, the Default
Organization View is assigned to it.

Also implements additional filtering in the candlepin proxies controller,
and several additional tests.
  • Loading branch information
wbclark committed Aug 27, 2024
1 parent e50aca7 commit c87acda
Show file tree
Hide file tree
Showing 5 changed files with 100 additions and 4 deletions.
14 changes: 12 additions & 2 deletions app/controllers/katello/api/rhsm/candlepin_proxies_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,16 @@ def enabled_repos

#api :POST, "/environments/:environment_id/consumers", N_("Register a consumer in environment")
def consumer_create
host = Katello::RegistrationManager.process_registration(rhsm_params, find_content_view_environments)
content_view_environments = find_content_view_environments
if content_view_environments.any? { |cve| cve.content_view.generated_for_repository_export? }
render json: {
displayMessage: _("Cannot register with a content view generated for repository export"),
errors: [_("Cannot register with a content view generated for repository export")]
}, status: :bad_request
return
end

host = Katello::RegistrationManager.process_registration(rhsm_params, content_view_environments)

host.reload

Expand Down Expand Up @@ -408,7 +417,8 @@ def find_activation_keys
def update_environments_from_facts(param_environments)
return if param_environments.blank?
new_envs = param_environments.map do |env|
get_content_view_environment("cp_id", env['id'])
cve = get_content_view_environment("cp_id", env['id'])
cve unless cve&.content_view&.generated_for_repository_export?
end
new_envs.compact!
Rails.logger.debug "Setting new content view environments for host #{@host.to_label}: #{new_envs.map(&:label)}"
Expand Down
40 changes: 40 additions & 0 deletions db/migrate/20240815080259_migrate_off_generated_content_views.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
class MigrateOffGeneratedContentViews < ActiveRecord::Migration[6.1]
def up
say_with_time "Migrating hosts off generated content views" do
migrate_hosts
end
end

def down
say "This migration cannot be reversed", true
end

private

def migrate_hosts
say_with_time "Migrating hosts..." do
generated_content_views = Katello::ContentView.where(generated_for: 'repository_export')

facets = Katello::Host::ContentFacet.joins(:content_view_environments)
facets = facets.where(katello_content_view_environments: { content_view_id: generated_content_views })
facets.find_each do |content_facet|
offending_cves = content_facet.content_view_environments.select { |cve| generated_content_views.include?(cve.content_view) }
valid_cves = content_facet.content_view_environments - offending_cves

if valid_cves.empty?
default_view = Katello::ContentView.find_by(name: "Default Organization View", organization: content_facet.host.organization)
if default_view
default_cve = default_view.content_view_environments.find_by(lifecycle_environment: content_facet.lifecycle_environments.first)
content_facet.update!(content_view_environments: [default_cve])
say "Replaced all content views with Default Organization View for host #{content_facet.host.name}", true
else
say "No Default Organization View found for host #{content_facet.host.name}. Skipping.", true
end
else
content_facet.update!(content_view_environments: valid_cves)
say "Removed offending content views for host #{content_facet.host.name}", true
end
end
end
end
end
29 changes: 27 additions & 2 deletions test/controllers/api/rhsm/candlepin_proxies_controller_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ module Katello
end
end

describe "register with a lifecycle environment" do
describe "register with a single lifecycle environment" do
before do
@facts = { 'network.hostname' => 'somehostname'}
@content_view_environment = ContentViewEnvironment.find(katello_content_view_environments(:library_default_view_environment).id)
Expand Down Expand Up @@ -122,7 +122,7 @@ module Katello
assert_response 400
end

it "should not register" do
it "should not register with dead services" do
::Katello::RegistrationManager.expects(:check_registration_services).returns(false)
::Katello::RegistrationManager.expects(:process_registration).never

Expand All @@ -131,6 +131,31 @@ module Katello

assert_response 500
end

it "should not register with a content view generated for repository export" do
organization = Organization.find(taxonomies(:empty_organization).id)
library = organization.library

generated_cv = FactoryBot.create(:katello_content_view, :generated_for => :repository_export, :organization => organization)
generated_cve = FactoryBot.create(:katello_content_view_environment,
:content_view => generated_cv,
:environment => library)

Resources::Candlepin::Consumer.stubs(:get)
::Katello::RegistrationManager.expects(:check_registration_services).returns(true)
::Katello::RegistrationManager.expects(:process_registration).never

post(
:consumer_create,
:params => {
:organization_id => organization.label,
:environment_id => generated_cve.cp_id,
:facts => @facts
}
)

assert_response 400
end
end

describe "update enabled_repos" do
Expand Down
10 changes: 10 additions & 0 deletions test/models/activation_key_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,16 @@ def setup
end
end

test "should not allow generated content view to be associated with activation key" do
generated_cv = FactoryBot.create(:katello_content_view, :generated_for => :repository_export, :organization => @dev_view.organization)

exception = assert_raises(ActiveRecord::RecordInvalid) do
@dev_key.update!(content_view: generated_cv)
end

assert_match(/Generated content views cannot be assigned to hosts or activation keys/, exception.message)
end

def test_search_name
activation_keys = ActivationKey.search_for("name = \"#{@dev_staging_view_key.name}\"")
assert_includes activation_keys, @dev_staging_view_key
Expand Down
11 changes: 11 additions & 0 deletions test/models/host/content_facet_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,17 @@ def test_audit_for_content_facet
content_facet_rec = host1.associated_audits.where(auditable_id: content_facet1.id)
assert content_facet_rec, "No associated audit record for content_facet"
end

def test_content_view_environments_not_generated_for_repository_export
generated_cv = FactoryBot.create(:katello_content_view, :generated_for => :repository_export, :organization => view.organization)
generated_cve = FactoryBot.create(:katello_content_view_environment, :content_view => generated_cv, :environment => library)

exception = assert_raises(ActiveRecord::RecordInvalid) do
content_facet.content_view_environments = [generated_cve]
end

assert_includes exception.message, "Content view '#{generated_cv.name}' is a generated content view, which cannot be assigned to hosts or activation keys."
end
end

class ContentFacetErrataTest < ContentFacetBase
Expand Down

0 comments on commit c87acda

Please sign in to comment.