Create groups in cfme when the appliance is using external authentication (ldap/ipa/ad)


#1

Hi,

Is there any docs or examples for creating groups when the CFME Appliance is using external authentication? (AD/LDAP/IdM)

If i do it manually, i search an user and then (if there is no error between cfme and external auth) i select the group from the returned list of groups for the user.

I checked:

And i don’t know how to do it yet.
If it can be done via api, it looks like the work-flow might be different compared with doing it from the webui.

Thanks in advance.


#2

Hi @Guillermo_Reartes,

You need to create the groups in both ManageIQ and the external provider. ManageIQ just performs a lookup by name on the group.

If you’re using LDAP (AD/ IPA/ IdM), you can use the net-ldap gem to create LDAP groups. In the example below, I’ve saved the LDAP host, port bind DN, bind DN password, and groups DN into instance variables. Note that IdM/ IPA uses the OpenLDAP ‘memberOf’ overlay, so we only need to update the ‘member’ attribute for a group:

require 'net/ldap'

begin
  group_name = "new-group"
  miq_request = $evm.root['miq_request'] || $evm.root['service_template_provision_task']
  
  requester = miq_request.miq_request.requester || miq_request.requester

  ldap = Net::LDAP.new 
  ldap.host = $evm.object['ldap_host']
  ldap.port= $evm.object['ldap_port']
  ldap.authenticate $evm.object['ldap_bind_dn'], $evm.object.decrypt('ldap_pass')
  
  user_dn  = requester.userid

  group_dn = "cn=#{group_name},#{$evm.object['group_dn']}"
  attr= {
    :cn => "#{group_name}",
    :objectClass => ["top","groupOfNames"],
    :member => user_dn
  }

  ldap.add(:dn => group_dn, :attributes => attr)
  
rescue => err
  $evm.log(:error, "[(#{err.class})#{err}]\n#{err.backtrace.join("\n")}")
  exit MIQ_ABORT
  
end

Once, you’ve created the group in the external provider, you can use the ManageIQ REST API to create a group matching the LDAP one. Here, I’ve saved the role name, ManageIQ user and ManageIQ password as instance variables, and I have a single overarching tenant:

require 'rest-client'
require 'json'

begin
  
  tenant = $evm.vmdb(:tenant).first
  group_name = "new-group"
  
  # Check if the group already exists, otherwise create it via the REST API
  group = $evm.vmdb(:miq_group).find_by_description(group_name)
  
  if group.nil?  
    # Create the group using the REST API
    url = "https://localhost/api/groups/"
    username = $evm.object['miq_rest_user']
    password = $evm.object.decrypt('miq_rest_pw')

    resource = RestClient::Resource.new(url, :user => username, :password => password, 
      :headers => {
        :content_type => 'json',
        :accept => 'json'
        }, :verify_ssl => false )

    data = {
      :action => "create",
      :resource => {
        :description => group_name,
        :role => { :name => "#{$evm.object['group_role']}" },
        :tenant => { :id => tenant.id }
        }
      }.to_json

    response = resource.post(data )
    $evm.log(:info, "API response: #{response}")
  end
  
  rescue => err
  $evm.log(:error, "[(#{err.class})#{err}]\n#{err.backtrace.join("\n")}")
  exit MIQ_ABORT

end

I hope this helps.