diff --git a/manifests/profile/base/docker.pp b/manifests/profile/base/docker.pp index 29f8b7531..67fbd71f3 100644 --- a/manifests/profile/base/docker.pp +++ b/manifests/profile/base/docker.pp @@ -47,6 +47,18 @@ # [*step*] # step defaults to hiera('step') # +# [*configure_libvirt_polkit*] +# Configures libvirt polkit to grant the kolla nova user access to the libvirtd unix domain socket on the host. +# Defaults to true when nova_compute service is enabled, false when nova_compute is disabled +# +# [*docker_nova_uid*] +# When configure_libvirt_polkit = true, the uid/gid of the nova user within the docker container. +# Defaults to 42436 +# +# [*services_enabled*] +# List of TripleO services enabled on the role. +# Defaults to hiera('services_names') +# class tripleo::profile::base::docker ( $docker_namespace = undef, $insecure_registry = false, @@ -55,7 +67,17 @@ class tripleo::profile::base::docker ( $configure_storage = true, $storage_options = '-s overlay2', $step = hiera('step'), + $configure_libvirt_polkit = undef, + $docker_nova_uid = 42436, + $services_enabled = hiera('service_names', []) ) { + + if $configure_libvirt_polkit == undef { + $configure_libvirt_polkit_real = 'nova_compute' in $services_enabled + } else { + $configure_libvirt_polkit_real = $configure_libvirt_polkit + } + if $step >= 1 { package {'docker': ensure => installed, @@ -130,4 +152,41 @@ class tripleo::profile::base::docker ( } } + if ($step >= 4 and $configure_libvirt_polkit_real) { + # Workaround for polkit authorization for libvirtd socket on host + # + # This creates a local user with the kolla nova uid, and sets the polkit rule to + # allow both it and the nova user from the nova rpms, should it exist (uid 162). + + group { 'docker_nova_group': + name => 'docker_nova', + gid => $docker_nova_uid + } -> + user { 'docker_nova_user': + name => 'docker_nova', + uid => $docker_nova_uid, + gid => $docker_nova_uid, + shell => '/sbin/nologin', + comment => 'OpenStack Nova Daemons', + groups => ['nobody'] + } + + # Similar to the polkit rule in the openstack-nova rpm spec + # but allow both the 'docker_nova' and 'nova' user + $docker_nova_polkit_rule = '// openstack-nova libvirt management permissions +polkit.addRule(function(action, subject) { + if (action.id == "org.libvirt.unix.manage" && + /^(docker_)?nova$/.test(subject.user)) { + return polkit.Result.YES; + } +}); +' + package {'polkit': + ensure => installed, + } -> + file {'/etc/polkit-1/rules.d/50-nova.rules': + content => $docker_nova_polkit_rule, + mode => '0644' + } + } } diff --git a/spec/classes/tripleo_profile_base_docker_spec.rb b/spec/classes/tripleo_profile_base_docker_spec.rb index 0b988f624..bb21055ec 100644 --- a/spec/classes/tripleo_profile_base_docker_spec.rb +++ b/spec/classes/tripleo_profile_base_docker_spec.rb @@ -124,6 +124,85 @@ describe 'tripleo::profile::base::docker' do } end + context 'with step 4 and configure_libvirt_polkit disabled' do + let(:params) { { + :step => 4, + :configure_libvirt_polkit => false + } } + it { + is_expected.to_not contain_group('docker_nova_group') + is_expected.to_not contain_user('docker_nova_user') + is_expected.to_not contain_package('polkit') + is_expected.to_not contain_file('/etc/polkit-1/rules.d/50-nova.rules') + } + end + + context 'with step 4 and configure_libvirt_polkit enabled' do + let(:params) { { + :step => 4, + :configure_libvirt_polkit => true + } } + it { + is_expected.to contain_group('docker_nova_group').with( + :name => 'docker_nova', + :gid => 42436 + ) + is_expected.to contain_user('docker_nova_user').with( + :name => 'docker_nova', + :uid => 42436, + :gid => 42436, + :shell => '/sbin/nologin', + :groups => ['nobody'] + ) + is_expected.to contain_package('polkit') + is_expected.to contain_file('/etc/polkit-1/rules.d/50-nova.rules') + } + end + + context 'with step 4 and nova_compute service installed' do + let(:params) { { + :step => 4, + :services_enabled => ['docker', 'nova_compute'] + } } + it { + is_expected.to contain_group('docker_nova_group').with( + :name => 'docker_nova', + :gid => 42436 + ) + is_expected.to contain_user('docker_nova_user').with( + :name => 'docker_nova', + :uid => 42436, + :gid => 42436, + :shell => '/sbin/nologin', + :groups => ['nobody'] + ) + is_expected.to contain_package('polkit') + is_expected.to contain_file('/etc/polkit-1/rules.d/50-nova.rules') + } + end + + context 'with step 4 and configure_libvirt_polkit enabled and docker_nova uid' do + let(:params) { { + :step => 4, + :configure_libvirt_polkit => true, + :docker_nova_uid => 12345 + } } + it { + is_expected.to contain_group('docker_nova_group').with( + :name => 'docker_nova', + :gid => 12345 + ) + is_expected.to contain_user('docker_nova_user').with( + :name => 'docker_nova', + :uid => 12345, + :gid => 12345, + :shell => '/sbin/nologin', + :groups => ['nobody'] + ) + is_expected.to contain_package('polkit') + is_expected.to contain_file('/etc/polkit-1/rules.d/50-nova.rules') + } + end end on_supported_os.each do |os, facts|