From e4cf30780f10e582bb0887862b3b2248ecef450b Mon Sep 17 00:00:00 2001 From: Bernhard Suttner Date: Wed, 29 Oct 2025 15:02:46 +0100 Subject: [PATCH] Fixes #38877 - Add Agama installer templates (SLES16) --- .../agama_default.erb | 39 ++++ .../partition_tables_templates/agama_lvm.erb | 61 ++++++ .../PXEGrub2/agama_default_pxegrub2.erb | 61 ++++++ .../PXELinux/agama_default_pxelinux.erb | 15 ++ .../finish/agama_default_finish.erb | 46 ++++ .../iPXE/agama_default_ipxe.erb | 26 +++ .../provision/agama_sles_default.erb | 132 ++++++++++++ .../snippet/agama_generic_interface.erb | 59 +++++ .../snippet/agama_kernel_options.erb | 49 +++++ .../snippet/agama_network_setup.erb | 111 ++++++++++ .../user_data/agama_default_user_data.erb | 49 +++++ test/unit/foreman/renderer/snapshots.yaml | 6 + .../Agama_default_PXEGrub2.host4dhcp.snap.txt | 17 ++ .../Agama_default_PXELinux.host4dhcp.snap.txt | 4 + .../Agama_default_finish.host4dhcp.snap.txt | 105 +++++++++ .../Agama_default_iPXE.host4dhcp.snap.txt | 10 + .../Agama_sles_default.host4dhcp.snap.txt | 202 ++++++++++++++++++ ...Agama_default_user_data.host4dhcp.snap.txt | 116 ++++++++++ 18 files changed, 1108 insertions(+) create mode 100644 app/views/unattended/partition_tables_templates/agama_default.erb create mode 100644 app/views/unattended/partition_tables_templates/agama_lvm.erb create mode 100644 app/views/unattended/provisioning_templates/PXEGrub2/agama_default_pxegrub2.erb create mode 100644 app/views/unattended/provisioning_templates/PXELinux/agama_default_pxelinux.erb create mode 100644 app/views/unattended/provisioning_templates/finish/agama_default_finish.erb create mode 100644 app/views/unattended/provisioning_templates/iPXE/agama_default_ipxe.erb create mode 100644 app/views/unattended/provisioning_templates/provision/agama_sles_default.erb create mode 100644 app/views/unattended/provisioning_templates/snippet/agama_generic_interface.erb create mode 100644 app/views/unattended/provisioning_templates/snippet/agama_kernel_options.erb create mode 100644 app/views/unattended/provisioning_templates/snippet/agama_network_setup.erb create mode 100644 app/views/unattended/provisioning_templates/user_data/agama_default_user_data.erb create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXEGrub2/Agama_default_PXEGrub2.host4dhcp.snap.txt create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXELinux/Agama_default_PXELinux.host4dhcp.snap.txt create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/finish/Agama_default_finish.host4dhcp.snap.txt create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/iPXE/Agama_default_iPXE.host4dhcp.snap.txt create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/provision/Agama_sles_default.host4dhcp.snap.txt create mode 100644 test/unit/foreman/renderer/snapshots/ProvisioningTemplate/user_data/Agama_default_user_data.host4dhcp.snap.txt diff --git a/app/views/unattended/partition_tables_templates/agama_default.erb b/app/views/unattended/partition_tables_templates/agama_default.erb new file mode 100644 index 00000000000..0119b27f0a4 --- /dev/null +++ b/app/views/unattended/partition_tables_templates/agama_default.erb @@ -0,0 +1,39 @@ +<%# +kind: ptable +name: Agama default +model: Ptable +oses: +- OpenSUSE +- SLES +%> +<% + pxe_loader = @host.pxe_loader || '' +-%> + +"drives": [ + { + "search": "*", + "partitions": [ + { + "search": "*", + "delete": true + }, + { + "filesystem": { "path": "/boot", "type": "ext4", "name": "boot" }, + "size": { "min": "2 GiB", "max": "4 GiB" } + }, +<%- if pxe_loader.include?('UEFI') -%> + { + "filesystem": { "path": "/boot/efi", "type": "vfat", "name": "vfat" }, + "size": "1 GiB" + }, +<%- end -%> + { + "generate": "default" + } + ] + } +], +"boot": { + "configure": false +} diff --git a/app/views/unattended/partition_tables_templates/agama_lvm.erb b/app/views/unattended/partition_tables_templates/agama_lvm.erb new file mode 100644 index 00000000000..6aab892df52 --- /dev/null +++ b/app/views/unattended/partition_tables_templates/agama_lvm.erb @@ -0,0 +1,61 @@ +<%# +kind: ptable +name: Agama LVM +model: Ptable +oses: +- OpenSUSE +- SLES +%> +<% + pxe_loader = @host.pxe_loader || '' +-%> + +"boot": { "configure": false }, +"drives": [ + { + "alias": "disk", + "search": "*", + "partitions": [ + { + "search": "*", + "delete": true + }, +<%- if pxe_loader.include?('UEFI') -%> + { + "filesystem": { "path": "/boot/efi", "type": "vfat" }, + "size": "1 GiB" + }, +<%- else -%> + { + "filesystem": { "path": "/boot/", "type": "ext4" }, + "size": "2 GiB" + }, +<%- end -%> + { + "alias": "pv", + "id": "lvm", + "size": { "min": "20 GiB" } + } + ] + } +], +"volumeGroups": [ + { + "name": "system", + "physicalVolumes": [ "pv" ], + "logicalVolumes": [ + { + "filesystem": { "path": "/", "type": "ext4", "name": "root" }, + "size": { "min": "10 GiB" } + }, + { + "filesystem": { "path": "/var", "type": "ext4", "name": "var" }, + "size": { "min": "2 GiB", "max": "10 GiB" } + }, + { + "filesystem": { "path": "swap", "type": "swap", "name": "swap" }, + "size": { "min": "1 GiB", "max": "8 GiB" } + } + ] + } +] diff --git a/app/views/unattended/provisioning_templates/PXEGrub2/agama_default_pxegrub2.erb b/app/views/unattended/provisioning_templates/PXEGrub2/agama_default_pxegrub2.erb new file mode 100644 index 00000000000..78991e1e26b --- /dev/null +++ b/app/views/unattended/provisioning_templates/PXEGrub2/agama_default_pxegrub2.erb @@ -0,0 +1,61 @@ +<%# +kind: PXEGrub2 +name: Agama default PXEGrub2 +model: ProvisioningTemplate +oses: +- OpenSUSE +- SLES +description: | + The template to render PXEGrub2 bootloader configuration for Agama based distributions. + The output is deployed on the host's subnet TFTP proxy. +-%> +# This file was deployed via '<%= template_name %>' template +<% + if !@host.pxe_loader_efi? + linuxcmd = "linux" + initrdcmd = "initrd" + else + linuxcmd = "linuxefi" + initrdcmd = "initrdefi" + end + kernel_options = snippet('agama_kernel_options').strip +-%> + +set default=<%= host_param('default_grub_install_entry') || 0 %> +set timeout=<%= host_param('loader_timeout') || 10 %> + +menuentry '<%= template_name %>' { + <%= linuxcmd %> <%= @kernel %> <%= kernel_options %> + <%= initrdcmd %> <%= @initrd %> +} + +<% +# Workaround for https://bugzilla.redhat.com/show_bug.cgi?id=1811561 and https://bugzilla.redhat.com/show_bug.cgi?id=1842893 +subnet = @host.provision_interface.subnet || @host.provision_interface.subnet6 +if subnet && subnet.httpboot + proxy_http_port = subnet.httpboot.httpboot_http_port + proxy_https_port = subnet.httpboot.httpboot_https_port + # Workaround for "no DNS server configured" https://bugzilla.redhat.com/show_bug.cgi?id=1842509 + proxy_host = dns_lookup(subnet.httpboot.hostname) +-%> +<% if proxy_http_port -%> +menuentry '<%= template_name %> EFI HTTP' --id efi_http { + <%= linuxcmd %> (http,<%= proxy_host %>:<%= proxy_http_port %>)/httpboot/<%= @kernel %> <%= kernel_options %> + <%= initrdcmd %> (http,<%= proxy_host %>:<%= proxy_http_port %>)/httpboot/<%= @initrd %> +} +<% else -%> +# Smart proxy does not have HTTPBoot feature with HTTP port enabled, skipping EFI HTTP boot menu entry +<% end -%> + +<% if proxy_https_port -%> +menuentry '<%= template_name %> EFI HTTPS' --id efi_https { + <%= linuxcmd %> (https,<%= proxy_host %>:<%= proxy_https_port %>)/httpboot/<%= @kernel %> <%= kernel_options %> + <%= initrdcmd %> (https,<%= proxy_host %>:<%= proxy_https_port %>)/httpboot/<%= @initrd %> +} +<% else -%> +# Smart proxy does not have HTTPBoot feature with HTTPS port enabled, skipping EFI HTTPS boot menu entry +<% end -%> + +<% end %> + +<%= snippet_if_exists(template_name + " custom menu") %> diff --git a/app/views/unattended/provisioning_templates/PXELinux/agama_default_pxelinux.erb b/app/views/unattended/provisioning_templates/PXELinux/agama_default_pxelinux.erb new file mode 100644 index 00000000000..940c77f7f50 --- /dev/null +++ b/app/views/unattended/provisioning_templates/PXELinux/agama_default_pxelinux.erb @@ -0,0 +1,15 @@ +<%# +kind: PXELinux +name: Agama default PXELinux +model: ProvisioningTemplate +oses: +- OpenSUSE +- SLES +description: | + The template to render PXELinux bootloader configuration for SLES and OpenSUSE distributions. + The output is deployed on the host's subnet TFTP proxy. +-%> +DEFAULT linux +LABEL linux + KERNEL <%= @kernel %> + APPEND initrd=<%= @initrd %> <%= snippet("agama_kernel_options").strip %> diff --git a/app/views/unattended/provisioning_templates/finish/agama_default_finish.erb b/app/views/unattended/provisioning_templates/finish/agama_default_finish.erb new file mode 100644 index 00000000000..d7dc5b4aef9 --- /dev/null +++ b/app/views/unattended/provisioning_templates/finish/agama_default_finish.erb @@ -0,0 +1,46 @@ +<%# +kind: finish +name: Agama default finish +model: ProvisioningTemplate +oses: +- OpenSUSE +- SLES +-%> +<% + pm_set = @host.puppet_server.present? + puppet_enabled = pm_set || host_param_true?('force-puppet') + salt_enabled = host_param('salt_master') ? true : false +-%> + +/usr/bin/hostnamectl set-hostname <%= @host.name %> + +<%= snippet_if_exists(template_name + " custom pre") -%> + +<%- if plugin_present?('katello') && host_param('kt_activation_keys') -%> +<%= snippet_if_exists("sles_register") -%> +<% end -%> + +<%= snippet('remote_execution_ssh_keys') -%> + +<% if plugin_present?('katello') && host_param_true?('enable-remote-execution-pull') -%> +<%= save_to_file('/root/remote_execution_pull_setup.sh', snippet('remote_execution_pull_setup'), verbatim: true) %> +chmod +x /root/remote_execution_pull_setup.sh +/root/remote_execution_pull_setup.sh +<% end -%> + +<%= snippet "blacklist_kernel_modules" -%> + +<% if puppet_enabled -%> +<%= snippet 'puppet_setup' -%> +<% end -%> + +<% if salt_enabled -%> +<%= snippet 'saltstack_setup' -%> +<% end -%> + +<%= snippet 'eject_cdrom' -%> + +<%= snippet_if_exists(template_name + " custom post") -%> + +# Mark the build as finished +<%= snippet 'built' -%> diff --git a/app/views/unattended/provisioning_templates/iPXE/agama_default_ipxe.erb b/app/views/unattended/provisioning_templates/iPXE/agama_default_ipxe.erb new file mode 100644 index 00000000000..ae0a1fb8335 --- /dev/null +++ b/app/views/unattended/provisioning_templates/iPXE/agama_default_ipxe.erb @@ -0,0 +1,26 @@ +#!gpxe +<%# +kind: iPXE +name: Agama default iPXE +model: ProvisioningTemplate +oses: +- SLES +- OpenSUSE +description: | + The template to render iPXE installation script for SLES and OpenSUSE + The output is deployed on the host's subnet TFTP proxy. + See https://ipxe.org/scripting for more details +-%> +echo Trying to ping Gateway: ${netX/gateway} +ping --count 1 ${netX/gateway} || echo Ping to Gateway failed or ping command not available. +echo Trying to ping DNS: ${netX/dns} +ping --count 1 ${netX/dns} || echo Ping to DNS failed or ping command not available. + +<% boot_files_uris = @host.operatingsystem.boot_files_uri(medium_provider) -%> +<% kernel = boot_files_uris[0] -%> +<% initrd = boot_files_uris[1] -%> + +<% subnet = @host.subnet -%> +kernel <%= kernel %> initrd=initrd.img <%= snippet("agama_kernel_options").strip %> +initrd <%= initrd %> +boot diff --git a/app/views/unattended/provisioning_templates/provision/agama_sles_default.erb b/app/views/unattended/provisioning_templates/provision/agama_sles_default.erb new file mode 100644 index 00000000000..588d152a9f2 --- /dev/null +++ b/app/views/unattended/provisioning_templates/provision/agama_sles_default.erb @@ -0,0 +1,132 @@ +<%# +kind: provision +name: Agama sles default +model: ProvisioningTemplate +oses: +- OpenSUSE +- SLES +-%> +<% + os_major = @host.operatingsystem.major.to_i + os_minor = @host.operatingsystem.minor.to_i + pm_set = @host.puppet_server.present? + puppet_enabled = pm_set || host_param_true?('force-puppet') + salt_enabled = host_param('salt_master') ? true : false +-%> +{ + "product": { + "id": "SLES" + }, + "hostname": { + "static": "<%= @host.name %>" + }, + "root": { + "hashedPassword": true, + "password": "<%= root_pass %>" + }, + "localization": { + "language": "en_US.UTF-8", + "keyboard": "us", + "timezone": "<%= host_param('time-zone') || 'Europe/London' %>" + }, + "software": { + "packages": ["openssh", "wget"] + }, + "network": { + "connections": [ + <%= indent(8, skip1: true) { snippet('agama_network_setup') } %> + ] + }, + "storage": { + <%= indent(8, skip1: true) { @host.diskLayout } %> + }, + "scripts": { + "post": [ + { + "name": "enable-sshd", + "chroot": true, + "content": ||| + #!/usr/bin/bash + systemctl enable sshd.service + ||| + }, + { + "name": "eject-cdrom", + "chroot": true, + "content": ||| + # eject bootdisk if this is requested provisioning method + <%= indent(20, skip1: true) { snippet 'eject_cdrom' } -%> + + ||| + }, + { + "name": "foreman-finish", + "chroot": true, + "content": ||| + #!/usr/bin/bash + <%- if host_param('http-proxy') -%> + export http_proxy="http://<%= host_param('http-proxy') %>:<%= host_param('http-proxy-port') -%>" + <%- if host_param('noproxy') -%> + export no_proxy="<%= host_param('http-proxy') %> <%= host_param('noproxy') -%>" + <%- end -%> + <%- end -%> + <%= indent(20, skip1: true) { snippet_if_exists(template_name + " custom finish pre") } -%> + <%- if plugin_present?('katello') && host_param('kt_activation_keys') -%> + <%= indent(20, skip1: true) { snippet_if_exists("sles_register") } -%> + <%- end -%> + + <%= indent(20, skip1: true) { snippet "blacklist_kernel_modules" } -%> + + # Fix agama vs puppet/salt cleaning the /etc/resolv.conf + # https://github.com/agama-project/agama/issues/2911 + cp /etc/resolv.conf /etc/resolv.conf.backup + + <%- if puppet_enabled -%> + <%= indent(20, skip1: true) { snippet 'puppet_setup' } -%> + # Fix agama vs puppet/salt cleaning the /etc/resolv.conf + # https://github.com/agama-project/agama/issues/2911 + cat /etc/resolv.conf.backup >/etc/resolv.conf + <%- end -%> + + <%- if salt_enabled -%> + <%= indent(20, skip1: true) { snippet 'saltstack_setup' } -%> + # Fix agama vs puppet/salt cleaning the /etc/resolv.conf + # https://github.com/agama-project/agama/issues/2911 + cat /etc/resolv.conf.backup >/etc/resolv.conf + <%- end -%> + + <%= indent(20, skip1: true) { snippet_if_exists(template_name + " custom finish post") } -%> + + rm -f /etc/resolv.conf.backup + echo "End of foreman-finish script" + ||| + }, + { + "name": "built", + "content": ||| + # Let foreman know that the build is complete + <%= indent(20, skip1: true) { snippet 'built' } -%> + + ||| + } + ], + "init": [ + { + "name": "foreman-init", + "content": ||| + #!/usr/bin/bash + <%= indent(20, skip1: true) { snippet_if_exists(template_name + " custom init pre") } -%> + <%= indent(20, skip1: true) { snippet('remote_execution_ssh_keys') } -%> + <%- if plugin_present?('katello') && host_param_true?('enable-remote-execution-pull') -%> + <%= indent(20, skip1: true) { save_to_file('/root/remote_execution_pull_setup.sh', snippet('remote_execution_pull_setup'), verbatim: true) } %> + chmod +x /root/remote_execution_pull_setup.sh + /root/remote_execution_pull_setup.sh + <%- end -%> + <%= indent(20, skip1: true) { snippet_if_exists(template_name + " custom init post") } -%> + + echo "End of foreman-init script" + ||| + } + ] + } +} diff --git a/app/views/unattended/provisioning_templates/snippet/agama_generic_interface.erb b/app/views/unattended/provisioning_templates/snippet/agama_generic_interface.erb new file mode 100644 index 00000000000..e320e28e8cb --- /dev/null +++ b/app/views/unattended/provisioning_templates/snippet/agama_generic_interface.erb @@ -0,0 +1,59 @@ +<%# +name: agama_generic_interface +model: ProvisioningTemplate +snippet: true +model: ProvisioningTemplate +kind: snippet +oses: +- SLES +- OpenSUSE +-%> + "id": "<%= @id %>", +<%- if @interface.identifier.present? -%> + "interface": "<%= @interface.identifier %>", +<%- end -%> + "method4": "<%= @dhcp ? 'auto' : (@subnet.nil? ? 'disabled' : 'manual') %>", + "method6": "<%= @dhcp6 ? 'auto' : (@subnet6.nil? ? 'disabled' : 'manual') %>", +<%- if @interface.mac.present? && !@interface.virtual? -%> + "macAddress": "<%= @interface.mac %>", +<%- end -%> +<%- +ips = [] +static_v4 = !@dhcp && !@subnet.nil? && !@interface.ip.nil? +ips.push("#{@interface.ip}/#{@subnet.cidr}") if static_v4 +static_v6 = !@dhcp6 && !@subnet6.nil? && !@interface.ip6.nil? +ips.push("#{@interface.ip6}/#{@subnet6.cidr}") if static_v6 +-%> +<%- if static_v4 || static_v6 -%> + "addresses": [<%= ips.map { |d| %("#{d}") }.join(", ") %>], +<%- if static_v4 && @subnet.gateway.present? -%> + "gateway4": "<%= @subnet.gateway %>", +<%- end -%> +<%- if static_v6 && @subnet6.gateway.present? -%> + "gateway6": "<%= @subnet6.gateway %>", +<%- end -%> + "ignoreAutoDns": true, +<%- else -%> + "ignoreAutoDns": false, +<%- end -%> +<%- if @interface.primary -%> +<%- + dns_servers = [] + dns_servers += @subnet.dns_servers if @subnet&.dns_servers + dns_servers += @subnet6.dns_servers if @subnet6&.dns_servers + dns_servers = dns_servers.compact.uniq +-%> + "nameservers": [<%= dns_servers.map { |d| %("#{d}") }.join(", ") %>], +<%- end -%> +<%- if @interface&.domain -%> + // Does currently break the agama installation wizard (complains about wrong 'storage' configuration) + // "dnsSearchlist": ["<%= @interface.domain %>"], +<%- end -%> +<%- if @subnet && @subnet.mtu.present? -%> + "mtu": <%= @subnet.mtu %>, +<%- elsif @subnet6 && @subnet6.mtu.present? -%> + "mtu": <%= @subnet6.mtu %>, +<%- end -%> + "status": "up", + "autoconnect": true, + "persistent": true diff --git a/app/views/unattended/provisioning_templates/snippet/agama_kernel_options.erb b/app/views/unattended/provisioning_templates/snippet/agama_kernel_options.erb new file mode 100644 index 00000000000..efd62b48678 --- /dev/null +++ b/app/views/unattended/provisioning_templates/snippet/agama_kernel_options.erb @@ -0,0 +1,49 @@ +<%# +kind: snippet +name: agama_kernel_options +model: ProvisioningTemplate +snippet: true +description: | + The list of kernel options for initrd appended to the bootloader kernel line on SUSE compatible distributions. + Typically renders to a string with the url where to fetch the OS installer answer files, e.g. + ip=dhcp showopts root=live:url --url https://media.local/suse/LiveOS/squashfs.img inst.install_url=url --url https://media.local/suse/install/ + inst.auto=http://foreman/unattended/provision?token=1234 + Custom options can be added by setting the array parameter agama_kernel_custom_options +-%> +<% +options = [] + +iface = @host.provision_interface +subnet4 = iface.subnet +subnet6 = iface.subnet6 + +if host_param('http-proxy') && host_param('http-proxy-port') + options << "proxy=http://" + host_param('http-proxy') + ":" + host_param('http-proxy-port') +elsif host_param('http-proxy') + options << "proxy=http://" + host_param('http-proxy') +end + +if subnet4.respond_to?(:dhcp_boot_mode?) and subnet4.dhcp_boot_mode? + options << "ip=dhcp" +elsif subnet4 && !subnet4.dhcp_boot_mode? + options << "ip=#{iface.ip}::#{subnet4.gateway}:#{subnet4.cidr} nameserver=#{subnet4.dns_primary}" +elsif subnet6 && subnet6.dhcp_boot_mode? + options << "ip=auto6" +elsif subnet6 && !subnet6.dhcp_boot_mode? + options << "ip=#{iface.ip6}::#{subnet6.gateway}:#{subnet6.cidr} nameserver=#{subnet6.dns_primary}" +end + +custom_options = [host_param('agama_kernel_custom_options')].flatten.compact + +options << "showopts" +options << "root=live:#{@mediapath}/LiveOS/squashfs.img" +options << "inst.install_url=#{@mediapath}/install/" +options << "inst.auto=#{foreman_url('provision')}" + +# FIPS +options.push('fips=1') if host_param_true?('fips_enabled') + +options.concat(custom_options) +-%> +<%# do not add newline after the next line %> +<%= options.join(' ') -%> diff --git a/app/views/unattended/provisioning_templates/snippet/agama_network_setup.erb b/app/views/unattended/provisioning_templates/snippet/agama_network_setup.erb new file mode 100644 index 00000000000..cd7160352e8 --- /dev/null +++ b/app/views/unattended/provisioning_templates/snippet/agama_network_setup.erb @@ -0,0 +1,111 @@ +<%# +kind: snippet +name: agama_network_setup +model: ProvisioningTemplate +snippet: true +description: | + This will configure your host networking, it configures your + primary interface as well as other NICs like BOND, BRIDGE, VLAN and Alias + interfaces. +oses: +- OpenSUSE +- SLES +-%> +<% +bonding_interfaces = [] +bridged_interfaces = [] +vlans_interfaces = [] +-%> + +<%# +##### Processing bond-interfaces ##### +-%> +<%- id = 0 -%> +<%- @host.bond_interfaces.each do | bond | -%> + <%- bonding_interfaces.push(bond.identifier) -%> + { +<%- result = snippet('agama_generic_interface', :variables => { + :interface => bond, + :id => "bond#{id}", + :subnet => bond.subnet, + :subnet6 => bond.subnet6, + :dhcp => bond.subnet.nil? ? false : bond.subnet.dhcp_boot_mode?, + :dhcp6 => bond.subnet6.nil? ? false : bond.subnet6.dhcp_boot_mode? }) -%> +<%= result %>, + "bond": { + "ports": <%= bond.attached_devices_identifiers.to_s %>, + <%- if bond&.bond_options.present? -%> + "options": "<%= bond.bond_options %>", + <% end -%> + "mode": "<%= bond.mode %>" + } + }, + <%- id += 1 -%> +<% end -%> + +<%# ##### Processing bridge interfaces ##### -%> +<%- id = 0 -%> +<%- @host.bridge_interfaces.each do | bridge | -%> +<%- next if bonding_interfaces.include?(bridge.identifier) -%> + <%- bridged_interfaces.push(bridge.identifier) -%> + { +<%- result = snippet('agama_generic_interface', :variables => { + :interface => bridge, + :id => "br#{id}", + :subnet => bridge.subnet, + :subnet6 => bridge.subnet6, + :dhcp => bridge.subnet.nil? ? false : bridge.subnet.dhcp_boot_mode?, + :dhcp6 => bridge.subnet6.nil? ? false : bridge.subnet6.dhcp_boot_mode? }) -%> +<%= result %>, + "bridge": { + "ports": <%= bridge.attached_devices_identifiers.to_s %>, + <%- # Currently no support for bridge options in the interface. -%> + } + }, + <%- id += 1 -%> +<%- end -%> + +<%# ##### Processing vlan interfaces ##### -%> +<%- id = 0 -%> +<%- @host.managed_interfaces.each do | vlan | -%> +<%- next if bonding_interfaces.include?(vlan.identifier) -%> +<%- next if bridged_interfaces.include?(vlan.identifier) -%> +<%- next if !vlan.virtual? -%> + <%- vlans_interfaces.push(vlan.identifier) -%> + { +<%- result = snippet('agama_generic_interface', :variables => { + :interface => vlan, + :id => "vlan#{id}", + :subnet => vlan.subnet, + :subnet6 => vlan.subnet6, + :dhcp => vlan.subnet.nil? ? false : vlan.subnet.dhcp_boot_mode?, + :dhcp6 => vlan.subnet6.nil? ? false : vlan.subnet6.dhcp_boot_mode? }) -%> +<%= result %>, + "vlan": { + "id": <%= vlan.tag %>, + "parent": "<%= vlan.attached_to %>" + } + }, + <%- id += 1 -%> +<%- end -%> + +<%# ##### Processing remaining interfaces (ethernets) ##### -%> +<%- id = 0 -%> +<%- interfaces_count = @host.managed_interfaces.size -%> +<%- @host.managed_interfaces.each do | interface | -%> +<%- next if bonding_interfaces.include?(interface.identifier) -%> +<%- next if bridged_interfaces.include?(interface.identifier) -%> +<%- next if vlans_interfaces.include?(interface.identifier) -%> + <%- interface_subnet = interface.subnet -%> + { +<%- result = snippet('agama_generic_interface', :variables => { + :interface => interface, + :id => "id#{id}", + :subnet => interface.subnet, + :subnet6 => interface.subnet6, + :dhcp => interface.subnet.nil? ? false : interface.subnet.dhcp_boot_mode?, + :dhcp6 => interface.subnet6.nil? ? false : interface.subnet6.dhcp_boot_mode? }) -%> +<%= result %> + }<%= "," unless (id + 1) == interfaces_count %> + <%- id += 1 -%> +<%- end -%> diff --git a/app/views/unattended/provisioning_templates/user_data/agama_default_user_data.erb b/app/views/unattended/provisioning_templates/user_data/agama_default_user_data.erb new file mode 100644 index 00000000000..e9d9487beb6 --- /dev/null +++ b/app/views/unattended/provisioning_templates/user_data/agama_default_user_data.erb @@ -0,0 +1,49 @@ +<%# +kind: user_data +name: Agama default user data +model: ProvisioningTemplate +oses: +- OpenSUSE +- SLES +description: | + This template is used during image based provisioning, when the image is configured to use user-data. + The output is a shell script that cloud-init runs to configures the VM + booted from the image. The image must have cloud-init installed in order for this to work. + This script can be used with OpenSUSE and SLES images. +-%> +<% + # safemode renderer does not support unary negation + puppet_enabled = !host_param_true?('skip-puppet-setup') && (host_puppet_server.present? || host_param_true?('force-puppet')) + salt_enabled = host_param('salt_master') ? true : false +-%> +#!/bin/bash + +<%= snippet_if_exists(template_name + " custom pre") -%> + +<%# Cloud instances frequently have incorrect hosts data %> +<%= snippet 'fix_hosts' -%> + +<% if @host.provision_method == 'image' && root_pass.present? -%> +# Install the root password +echo 'root:<%= root_pass -%>' | /usr/sbin/chpasswd -e +<% end -%> + +<%= snippet('remote_execution_ssh_keys') -%> + +<%= snippet "blacklist_kernel_modules" -%> + +<% if puppet_enabled -%> +<% if host_param_true?('enable-official-openvox8-repo') -%> +<%= snippet 'puppetlabs_repo' -%> +<% end -%> +<%= snippet 'puppet_setup' -%> +<% end -%> + +<% if salt_enabled -%> +<%= snippet 'saltstack_setup' -%> +<% end -%> + +<%= snippet_if_exists(template_name + " custom post") -%> + +# Mark the build as finished +<%= snippet 'built' -%> diff --git a/test/unit/foreman/renderer/snapshots.yaml b/test/unit/foreman/renderer/snapshots.yaml index b552d706256..c0f40d3e24d 100644 --- a/test/unit/foreman/renderer/snapshots.yaml +++ b/test/unit/foreman/renderer/snapshots.yaml @@ -1,6 +1,11 @@ # Edit this file and then run: rake snapshots:generate RAILS_ENV=test files: + - PXEGrub2/agama_default_pxegrub2.erb + - PXELinux/agama_default_pxelinux.erb + - finish/agama_default_finish.erb + - provision/agama_sles_default.erb + - user_data/agama_default_user_data.erb - provision/alterator_default.erb - cloud_init/cloud_init_default.erb - PXELinux/pxelinux_global_default.erb @@ -67,6 +72,7 @@ files: - PXELinux/preseed_default_pxelinux_autoinstall.erb - PXEGrub2/preseed_default_pxegrub2_autoinstall.erb - user_data/preseed_autoinstall_cloud_init.erb + - iPXE/agama_default_ipxe.erb - iPXE/autoyast_default_ipxe.erb - iPXE/ipxe_default_local_boot.erb - iPXE/ipxe_global_default.erb diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXEGrub2/Agama_default_PXEGrub2.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXEGrub2/Agama_default_PXEGrub2.host4dhcp.snap.txt new file mode 100644 index 00000000000..eab4b0061b0 --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXEGrub2/Agama_default_PXEGrub2.host4dhcp.snap.txt @@ -0,0 +1,17 @@ +# This file was deployed via 'Agama default PXEGrub2' template + +set default=0 +set timeout=10 + +menuentry 'Agama default PXEGrub2' { + linux boot/centos-mirror-nrm0GtSX1ZC5-vmlinuz ip=dhcp showopts root=live:url --url http://mirror.centos.org/centos/7/os/x86_64/LiveOS/squashfs.img inst.install_url=url --url http://mirror.centos.org/centos/7/os/x86_64/install/ inst.auto=http://foreman.example.com/unattended/provision fips=1 + initrd boot/centos-mirror-nrm0GtSX1ZC5-initrd.img +} + +# Smart proxy does not have HTTPBoot feature with HTTP port enabled, skipping EFI HTTP boot menu entry + +# Smart proxy does not have HTTPBoot feature with HTTPS port enabled, skipping EFI HTTPS boot menu entry + + + + diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXELinux/Agama_default_PXELinux.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXELinux/Agama_default_PXELinux.host4dhcp.snap.txt new file mode 100644 index 00000000000..358d4ec860f --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/PXELinux/Agama_default_PXELinux.host4dhcp.snap.txt @@ -0,0 +1,4 @@ +DEFAULT linux +LABEL linux + KERNEL boot/centos-mirror-nrm0GtSX1ZC5-vmlinuz + APPEND initrd=boot/centos-mirror-nrm0GtSX1ZC5-initrd.img ip=dhcp showopts root=live:url --url http://mirror.centos.org/centos/7/os/x86_64/LiveOS/squashfs.img inst.install_url=url --url http://mirror.centos.org/centos/7/os/x86_64/install/ inst.auto=http://foreman.example.com/unattended/provision fips=1 diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/finish/Agama_default_finish.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/finish/Agama_default_finish.host4dhcp.snap.txt new file mode 100644 index 00000000000..0b75ef508c7 --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/finish/Agama_default_finish.host4dhcp.snap.txt @@ -0,0 +1,105 @@ + +/usr/bin/hostnamectl set-hostname snapshot-ipv4-dhcp-el7 + + + + +# Select package manager for the OS (sets the $PKG_MANAGER* variables) +if [ -z "$PKG_MANAGER" ]; then + if [ -f /etc/os-release ] ; then + . /etc/os-release + fi + + if [ "${NAME%.*}" = 'FreeBSD' ]; then + PKG_MANAGER='pkg' + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} delete -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} install -y" + elif [ -f /etc/fedora-release -o -f /etc/redhat-release -o -f /etc/amazon-linux-release -o -f /etc/system-release ]; then + PKG_MANAGER='dnf' + if [ -f /etc/redhat-release -a "${VERSION_ID%.*}" -le 7 ]; then + PKG_MANAGER='yum' + elif [ -f /etc/system-release ]; then + PKG_MANAGER='yum' + fi + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} upgrade -y" + elif [ -f /etc/debian_version ]; then + PKG_MANAGER='apt-get' + PKG_MANAGER_INSTALL="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' -o APT::Get::Upgrade-Allow-New='true' upgrade -y" + elif [ -f /etc/arch-release ]; then + PKG_MANAGER='pacman' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --noconfirm -S" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --noconfirm -R" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --noconfirm -S" + elif [ x$ID = xopensuse-tumbleweed -o x$ID = xsles ]; then + PKG_MANAGER='zypper' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --non-interactive install --auto-agree-with-licenses" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --non-interactive remove" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --non-interactive update" + fi +fi + + + +echo "blacklist amodule" >> /etc/modprobe.d/blacklist.conf + +if [ -f /usr/bin/dnf ]; then + dnf -y install puppet +else + yum -t -y install puppet +fi + +cat > /etc/puppet/puppet.conf << EOF +[main] +vardir = /var/lib/puppet +logdir = /var/log/puppet +rundir = /var/run/puppet +ssldir = \$vardir/ssl + +[agent] +pluginsync = true +report = true +certname = snapshot-ipv4-dhcp-el7 + +EOF + + +puppet_unit=puppet +/usr/bin/systemctl list-unit-files | grep -q puppetagent && puppet_unit=puppetagent +/usr/bin/systemctl enable ${puppet_unit} + +# export a custom fact called 'is_installer' to allow detection of the installer environment in Puppet modules +export FACTER_is_installer=true +# passing a non-existent tag like "no_such_tag" to the puppet agent only initializes the node +# You can select specific tag(s) with the "run-puppet-in-installer-tags" parameter +# or set a full puppet run by setting "run-puppet-in-installer" = true +echo "Performing initial puppet run for --tags no_such_tag" +/usr/bin/puppet agent --config /etc/puppet/puppet.conf --onetime --tags no_such_tag --no-daemonize + + + + +# Mark the build as finished +if [ -x /usr/bin/curl ]; then + /usr/bin/curl -o /dev/null -H 'Content-Type: text/plain' --fail --noproxy \* --silent 'http://foreman.example.com/unattended/built' +elif [ -x /usr/bin/wget ]; then + /usr/bin/wget -q -O /dev/null --method POST --header 'Content-Type: text/plain' --no-proxy 'http://foreman.example.com/unattended/built' +else + wget -q -O /dev/null --header 'Content-Type: text/plain' 'http://foreman.example.com/unattended/built' +fi +FINAL_STATUS=$? + +if [ -x "$(command -v subscription-manager)" ] ; then + subscription-manager facts --update + SUB_MAN_STATUS=$? + + if [ $FINAL_STATUS -eq 0 ]; then + FINAL_STATUS=$SUB_MAN_STATUS + fi +fi + +(exit $FINAL_STATUS); diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/iPXE/Agama_default_iPXE.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/iPXE/Agama_default_iPXE.host4dhcp.snap.txt new file mode 100644 index 00000000000..41fe57b4222 --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/iPXE/Agama_default_iPXE.host4dhcp.snap.txt @@ -0,0 +1,10 @@ +#!gpxe +echo Trying to ping Gateway: ${netX/gateway} +ping --count 1 ${netX/gateway} || echo Ping to Gateway failed or ping command not available. +echo Trying to ping DNS: ${netX/dns} +ping --count 1 ${netX/dns} || echo Ping to DNS failed or ping command not available. + + +kernel http://mirror.centos.org/centos/7/os/x86_64/images/pxeboot/vmlinuz initrd=initrd.img ip=dhcp showopts root=live:url --url http://mirror.centos.org/centos/7/os/x86_64/LiveOS/squashfs.img inst.install_url=url --url http://mirror.centos.org/centos/7/os/x86_64/install/ inst.auto=http://foreman.example.com/unattended/provision fips=1 +initrd http://mirror.centos.org/centos/7/os/x86_64/images/pxeboot/initrd.img +boot diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/provision/Agama_sles_default.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/provision/Agama_sles_default.host4dhcp.snap.txt new file mode 100644 index 00000000000..d1142cb91c6 --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/provision/Agama_sles_default.host4dhcp.snap.txt @@ -0,0 +1,202 @@ +{ + "product": { + "id": "SLES" + }, + "hostname": { + "static": "snapshot-ipv4-dhcp-el7" + }, + "root": { + "hashedPassword": true, + "password": "$1$rtd8Ub7R$5Ohzuy8WXlkaK9cA2T1wb0" + }, + "localization": { + "language": "en_US.UTF-8", + "keyboard": "us", + "timezone": "Europe/London" + }, + "software": { + "packages": ["openssh", "wget"] + }, + "network": { + "connections": [ + + + + + { + "id": "id0", + "interface": "eth0", + "method4": "auto", + "method6": "disabled", + "macAddress": "00-f0-54-1a-7e-e0", + "ignoreAutoDns": false, + "nameservers": ["192.168.42.2", "192.168.42.3"], + // Does currently break the agama installation wizard (complains about wrong 'storage' configuration) + // "dnsSearchlist": ["snap.example.com"], + "mtu": 1342, + "status": "up", + "autoconnect": true, + "persistent": true + + } + + ] + }, + "storage": { + zerombr + clearpart --all --initlabel + part /boot --fstype ext3 --size=100 --asprimary + part / --fstype ext3 --size=1024 --grow + part swap --recommended + }, + "scripts": { + "post": [ + { + "name": "enable-sshd", + "chroot": true, + "content": ||| + #!/usr/bin/bash + systemctl enable sshd.service + ||| + }, + { + "name": "eject-cdrom", + "chroot": true, + "content": ||| + # eject bootdisk if this is requested provisioning method + + ||| + }, + { + "name": "foreman-finish", + "chroot": true, + "content": ||| + #!/usr/bin/bash + + echo "blacklist amodule" >> /etc/modprobe.d/blacklist.conf + + # Fix agama vs puppet/salt cleaning the /etc/resolv.conf + # https://github.com/agama-project/agama/issues/2911 + cp /etc/resolv.conf /etc/resolv.conf.backup + + if [ -f /usr/bin/dnf ]; then + dnf -y install puppet + else + yum -t -y install puppet + fi + + cat > /etc/puppet/puppet.conf << EOF + [main] + vardir = /var/lib/puppet + logdir = /var/log/puppet + rundir = /var/run/puppet + ssldir = \$vardir/ssl + + [agent] + pluginsync = true + report = true + certname = snapshot-ipv4-dhcp-el7 + + EOF + + + puppet_unit=puppet + /usr/bin/systemctl list-unit-files | grep -q puppetagent && puppet_unit=puppetagent + /usr/bin/systemctl enable ${puppet_unit} + + # export a custom fact called 'is_installer' to allow detection of the installer environment in Puppet modules + export FACTER_is_installer=true + # passing a non-existent tag like "no_such_tag" to the puppet agent only initializes the node + # You can select specific tag(s) with the "run-puppet-in-installer-tags" parameter + # or set a full puppet run by setting "run-puppet-in-installer" = true + echo "Performing initial puppet run for --tags no_such_tag" + /usr/bin/puppet agent --config /etc/puppet/puppet.conf --onetime --tags no_such_tag --no-daemonize + # Fix agama vs puppet/salt cleaning the /etc/resolv.conf + # https://github.com/agama-project/agama/issues/2911 + cat /etc/resolv.conf.backup >/etc/resolv.conf + + + + rm -f /etc/resolv.conf.backup + echo "End of foreman-finish script" + ||| + }, + { + "name": "built", + "content": ||| + # Let foreman know that the build is complete + if [ -x /usr/bin/curl ]; then + /usr/bin/curl -o /dev/null -H 'Content-Type: text/plain' --fail --noproxy \* --silent 'http://foreman.example.com/unattended/built' + elif [ -x /usr/bin/wget ]; then + /usr/bin/wget -q -O /dev/null --method POST --header 'Content-Type: text/plain' --no-proxy 'http://foreman.example.com/unattended/built' + else + wget -q -O /dev/null --header 'Content-Type: text/plain' 'http://foreman.example.com/unattended/built' + fi + FINAL_STATUS=$? + + if [ -x "$(command -v subscription-manager)" ] ; then + subscription-manager facts --update + SUB_MAN_STATUS=$? + + if [ $FINAL_STATUS -eq 0 ]; then + FINAL_STATUS=$SUB_MAN_STATUS + fi + fi + + (exit $FINAL_STATUS); + + ||| + } + ], + "init": [ + { + "name": "foreman-init", + "content": ||| + #!/usr/bin/bash + + # Select package manager for the OS (sets the $PKG_MANAGER* variables) + if [ -z "$PKG_MANAGER" ]; then + if [ -f /etc/os-release ] ; then + . /etc/os-release + fi + + if [ "${NAME%.*}" = 'FreeBSD' ]; then + PKG_MANAGER='pkg' + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} delete -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} install -y" + elif [ -f /etc/fedora-release -o -f /etc/redhat-release -o -f /etc/amazon-linux-release -o -f /etc/system-release ]; then + PKG_MANAGER='dnf' + if [ -f /etc/redhat-release -a "${VERSION_ID%.*}" -le 7 ]; then + PKG_MANAGER='yum' + elif [ -f /etc/system-release ]; then + PKG_MANAGER='yum' + fi + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} upgrade -y" + elif [ -f /etc/debian_version ]; then + PKG_MANAGER='apt-get' + PKG_MANAGER_INSTALL="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' -o APT::Get::Upgrade-Allow-New='true' upgrade -y" + elif [ -f /etc/arch-release ]; then + PKG_MANAGER='pacman' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --noconfirm -S" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --noconfirm -R" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --noconfirm -S" + elif [ x$ID = xopensuse-tumbleweed -o x$ID = xsles ]; then + PKG_MANAGER='zypper' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --non-interactive install --auto-agree-with-licenses" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --non-interactive remove" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --non-interactive update" + fi + fi + + + echo "End of foreman-init script" + ||| + } + ] + } +} diff --git a/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/user_data/Agama_default_user_data.host4dhcp.snap.txt b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/user_data/Agama_default_user_data.host4dhcp.snap.txt new file mode 100644 index 00000000000..d71119401d9 --- /dev/null +++ b/test/unit/foreman/renderer/snapshots/ProvisioningTemplate/user_data/Agama_default_user_data.host4dhcp.snap.txt @@ -0,0 +1,116 @@ +#!/bin/bash + + + +echo "snapshot-ipv4-dhcp-el7" > /etc/hostname + +hostname snapshot-ipv4-dhcp-el7 + +cat > /etc/hosts << EOF +127.0.0.1 snapshot-ipv4-dhcp-el7 snapshot-ipv4-dhcp-el7 localhost localhost.localdomain +::1 ip6-localhost ip6-loopback +fe00::0 ip6-localnet +ff00::0 ip6-mcastprefix +ff02::1 ip6-allnodes +ff02::2 ip6-allrouters +EOF + + + +# Select package manager for the OS (sets the $PKG_MANAGER* variables) +if [ -z "$PKG_MANAGER" ]; then + if [ -f /etc/os-release ] ; then + . /etc/os-release + fi + + if [ "${NAME%.*}" = 'FreeBSD' ]; then + PKG_MANAGER='pkg' + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} delete -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} install -y" + elif [ -f /etc/fedora-release -o -f /etc/redhat-release -o -f /etc/amazon-linux-release -o -f /etc/system-release ]; then + PKG_MANAGER='dnf' + if [ -f /etc/redhat-release -a "${VERSION_ID%.*}" -le 7 ]; then + PKG_MANAGER='yum' + elif [ -f /etc/system-release ]; then + PKG_MANAGER='yum' + fi + PKG_MANAGER_INSTALL="${PKG_MANAGER} install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} upgrade -y" + elif [ -f /etc/debian_version ]; then + PKG_MANAGER='apt-get' + PKG_MANAGER_INSTALL="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' install -y" + PKG_MANAGER_REMOVE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' remove -y" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} -o 'Dpkg::Options::=--force-confdef' -o 'Dpkg::Options::=--force-confold' -o APT::Get::Upgrade-Allow-New='true' upgrade -y" + elif [ -f /etc/arch-release ]; then + PKG_MANAGER='pacman' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --noconfirm -S" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --noconfirm -R" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --noconfirm -S" + elif [ x$ID = xopensuse-tumbleweed -o x$ID = xsles ]; then + PKG_MANAGER='zypper' + PKG_MANAGER_INSTALL="${PKG_MANAGER} --non-interactive install --auto-agree-with-licenses" + PKG_MANAGER_REMOVE="${PKG_MANAGER} --non-interactive remove" + PKG_MANAGER_UPGRADE="${PKG_MANAGER} --non-interactive update" + fi +fi + + +echo "blacklist amodule" >> /etc/modprobe.d/blacklist.conf + +if [ -f /usr/bin/dnf ]; then + dnf -y install puppet +else + yum -t -y install puppet +fi + +cat > /etc/puppet/puppet.conf << EOF +[main] +vardir = /var/lib/puppet +logdir = /var/log/puppet +rundir = /var/run/puppet +ssldir = \$vardir/ssl + +[agent] +pluginsync = true +report = true +certname = snapshot-ipv4-dhcp-el7 + +EOF + + +puppet_unit=puppet +/usr/bin/systemctl list-unit-files | grep -q puppetagent && puppet_unit=puppetagent +/usr/bin/systemctl enable ${puppet_unit} + +# export a custom fact called 'is_installer' to allow detection of the installer environment in Puppet modules +export FACTER_is_installer=true +# passing a non-existent tag like "no_such_tag" to the puppet agent only initializes the node +# You can select specific tag(s) with the "run-puppet-in-installer-tags" parameter +# or set a full puppet run by setting "run-puppet-in-installer" = true +echo "Performing initial puppet run for --tags no_such_tag" +/usr/bin/puppet agent --config /etc/puppet/puppet.conf --onetime --tags no_such_tag --no-daemonize + + + +# Mark the build as finished +if [ -x /usr/bin/curl ]; then + /usr/bin/curl -o /dev/null -H 'Content-Type: text/plain' --fail --noproxy \* --silent 'http://foreman.example.com/unattended/built' +elif [ -x /usr/bin/wget ]; then + /usr/bin/wget -q -O /dev/null --method POST --header 'Content-Type: text/plain' --no-proxy 'http://foreman.example.com/unattended/built' +else + wget -q -O /dev/null --header 'Content-Type: text/plain' 'http://foreman.example.com/unattended/built' +fi +FINAL_STATUS=$? + +if [ -x "$(command -v subscription-manager)" ] ; then + subscription-manager facts --update + SUB_MAN_STATUS=$? + + if [ $FINAL_STATUS -eq 0 ]; then + FINAL_STATUS=$SUB_MAN_STATUS + fi +fi + +(exit $FINAL_STATUS);