In today's post, we'll explore a PowerShell script that automates the LDAPS configuration (LDAP over SSL) on a vCenter Server. This script, named Configure-VcIdentitySourceLdaps.ps1, performs various tasks, including connecting to a vCenter Server, retrieving certificates from a domain controller, and configuring LDAPS with SSO (Single Sign-On).
Let's dive into the details of the script and understand its key components:
Logging Function: Write-Log
Function Write-Log {
[CmdletBinding()]
param(
[Parameter(Mandatory=$true)]
[string]$Value,
[switch]$ErrorType,
[switch]$SuccessType
)
$date = Get-Date -Format s
$fdate = Get-Date -Format dd-MM-yyyy
$currentFolder = Get-Location
$logFile = "$currentFolder\logs\logfile.txt"
if ((Test-Path -Path "$currentFolder\Logs") -like "False") {
New-Item -ItemType Directory -Path "$currentFolder\Logs" | Out-Null
}
if ($ErrorType) {
Write-Host "$date - ERROR: $Value" -ForegroundColor Red
Out-File -InputObject "$date - ERROR: $Value" -FilePath $LogFile -Append -Encoding utf8
}
elseif ($SuccessType) {
Write-Host "$date - ERROR: $Value" -ForegroundColor Green
Out-File -InputObject "$date - ERROR: $Value" -FilePath $LogFile -Append -Encoding utf8
} else {
Write-Host "$date - INFO: $Value" -ForegroundColor White
Out-File -InputObject "$date - INFO: $Value" -FilePath $LogFile -Append -Encoding utf8
}
}
The script begins with a custom logging function named Write-Log. This function logs messages with timestamps and differentiates between error, success, and informational messages. It creates a log file in the 'logs' directory, ensuring that the logs are organized and easy to review.
LDAPS Configuration Function: Configure-VcIdentitySourceLdaps
Function Configure-VcIdentitySourceLdaps {
[CmdletBinding()]
param (
[Parameter(Mandatory=$true)][string]$vcenter,
[Parameter(Mandatory=$true)][string]$vcenter_username,
[Parameter(Mandatory=$true)][string]$vcenter_password,
[Parameter(Mandatory=$true)][string]$vcenter_root_password,
[Parameter(Mandatory=$true)][string]$primary_server_url,
[string]$secondary_server_url,
[Parameter(Mandatory=$true)][string]$domain,
[Parameter(Mandatory=$true)][string]$domain_user,
[Parameter(Mandatory=$true)][string]$domain_password,
[Parameter(Mandatory=$true)][string]$base_user_dn,
[Parameter(Mandatory=$true)][string]$base_group_dn
)
try {
$currentFolder = Get-Location
$certFilePathSource = "$currentFolder\ldaps.cer"
$certFilePathDestination = "/tmp/ldaps.cer"
$tempBashFileSource = "$currentFolder\bash.sh"
$tempBashFileDestination = "/tmp/bash.sh"
# Connect to vCenter Server
Connect-VIServer -Server $vcenter -User $vcenter_username -Password $vcenter_password -ErrorAction Stop | Out-Null
Write-Log -Value "Successfully connected to $($vcenter)" -SuccessType -ErrorAction Stop
# Query vCenter VM that matches FQDN as hostname
$vCenterVM = Get-VM | Where-Object {$_.ExtensionData.Guest.hostname -eq $vcenter} -ErrorAction Stop
# Retrieve certificate from domain controller
$getRootCert = "openssl s_client -connect $($primary_server_url -replace "ldaps://") -showcerts"
$output = Invoke-VMScript -ScriptText $getRootCert -vm $vCenterVM -GuestUser "root" -GuestPassword $vcenter_root_password -ErrorAction Stop
# Define the begin and end markers
$beginMarker = "-----BEGIN CERTIFICATE-----"
$endMarker = "-----END CERTIFICATE-----"
# Initialize variables to store certificate positions
$beginIndex = 0
$endIndex = 0
$certificates = @()
# Find all occurrences of begin and end markers
while (($beginIndex = $output.ScriptOutput.IndexOf($beginMarker, $endIndex)) -ne -1) {
$beginIndex += $beginMarker.Length
$endIndex = $output.ScriptOutput.IndexOf($endMarker, $beginIndex)
$endIndex += $endMarker.Length + 2
if ($endIndex -ne -1) {
# Include the begin and end markers in the certificate
$certificate = $output.ScriptOutput.Substring($beginIndex - $beginMarker.Length, $endIndex - $beginIndex + $endMarker.Length)
$certificates += $certificate
}
}
# Output the extracted certificates
foreach ($cert in $certificates) {
Write-Log -Value "Certificate:" -ErrorAction Stop
Write-Log -Value $cert -ErrorAction Stop
}
# Select the last certificate in the chain (if needed)
$lastCertificate = $certificates[-1]
Write-Log -Value "Last Certificate:" -ErrorAction Stop
Write-Log -Value $lastCertificate -ErrorAction Stop
# Export ldaps certificate
$lastCertificate | Out-File -FilePath $certFilePathSource -Encoding ascii -ErrorAction Stop
# Copy certificate to vCenter server
Copy-VMGuestFile -VM $vCenterVM -Source $certFilePathSource -Destination $certFilePathDestination -LocalToGuest -GuestUser "root" -GuestPassword $vcenter_root_password -Force -ErrorAction Stop
# Checking if secondary server url is used.
if ($secondary_server_url) {
$FileOutput = "/opt/vmware/bin/sso-config.sh -add_identity_source -type adldap -baseUserDN $base_user_dn -baseGroupDN $base_group_dn -domain $domain -alias $($domain.split('.')[0]) -username $domain_user -password $domain_password -primaryURL $primary_server_url -secondaryURL $secondary_server_url -useSSL true -sslCert $certFilePathDestination"
} else {
$FileOutput = "/opt/vmware/bin/sso-config.sh -add_identity_source -type adldap -baseUserDN $base_user_dn -baseGroupDN $base_group_dn -domain $domain -alias $($domain.split('.')[0]) -username $domain_user -password $domain_password -primaryURL $primary_server_url -useSSL true -sslCert $certFilePathDestination"
}
# Create bash file to configure SSO on the vCenter server
$FileOutput | Out-File -FilePath "bash.sh" -ErrorAction Stop -Force -Encoding ascii
# Copy bash file to the vCenter server
Copy-VMGuestFile -VM $vCenterVM -Source $tempBashFileSource -Destination $tempBashFileDestination -LocalToGuest -GuestUser "root" -GuestPassword $vcenter_root_password -Force -ErrorAction Stop
Write-Log -Value "Configuring execution permissions on /tmp/bash.sh file." -ErrorAction Stop
$setPermission = "chmod +x $tempBashFileDestination"
$output = Invoke-VMScript -ScriptText $setPermission -vm $vCenterVM -GuestUser "root" -GuestPassword $vcenter_root_password -ErrorAction Stop
# Configure SSO on the vCenter Server
$configureSso = "/tmp/bash.sh"
$output = Invoke-VMScript -ScriptText $configureSso -vm $vCenterVM -GuestUser "root" -GuestPassword $vcenter_root_password -ErrorAction Stop
if($output.ScriptOutput -like "*ERROR*"){
Write-Log -Value $output.ScriptOutput -ErrorType -ErrorAction Stop
return
}else{
Write-Log -Value "SSO has been configured successfully on vCenter $vcenter_fqdn" -SuccessType -ErrorAction Stop
}
# Removing temporary bash file and ldaps.cer from source.
Write-Log -Value "Performing cleanup of temp files on source and destination"
$tempBashFileSource | Remove-Item -Force -Confirm:$false
$certFilePathSource | Remove-Item -Force -Confirm:$false
$removeTempFiles = "rm $certFilePathDestination $tempBashFileDestination"
$output = Invoke-VMScript -ScriptText $removeTempFiles -vm $vCenterVM -GuestUser "root" -GuestPassword $vcenter_root_password -ErrorAction Stop
# Disconnecting from vCenter Server.
Disconnect-VIServer -Server * -Confirm:$false -Force -ErrorAction Stop
} catch {
Write-Log -Value $_ -ErrorType -ErrorAction Stop
}
}
This function is the heart of the script, responsible for setting up LDAPS on the vCenter Server. Let's break down its steps:
-
Connection to vCenter Server:
-
Uses Connect-VIServer cmdlet to establish a connection to the vCenter Server.
-
Logs a success message upon successful connection.
-
-
Querying vCenter VM:
- Retrieves the VM object representing the vCenter Server using Get-VM and filtering based on the FQDN.
-
Retrieving Certificates:
-
Invokes a script on the vCenter VM using Invoke-VMScript to obtain certificates from the primary domain controller.
-
Parses the output to extract individual certificates.
-
-
Exporting Certificates:
- Saves the last certificate in the chain to a local file (ldaps.cer) for later use.
-
Copying Certificates to vCenter:
- Uses Copy-VMGuestFile to transfer the certificate file to the vCenter Server.
-
Creating Bash Script:
- Generates a Bash script (bash.sh) containing SSO configuration commands based on the provided parameters.
-
Copying Bash Script to vCenter:
- Transfers the Bash script to the vCenter Server using Copy-VMGuestFile.
-
Setting Execution Permissions:
- Grants execution permissions to the Bash script on the vCenter Server.
-
Configuring SSO:
-
Executes the Bash script on the vCenter Server to configure LDAPS and SSO.
-
Logs success or failure messages based on the script output.
-
-
Cleanup:
- Removes temporary files (bash.sh and ldaps.cer) from the source and destination.
-
Disconnecting from vCenter Server:
- Uses Disconnect-VIServer to close the connection to the vCenter Server.
Executing the Script:
The script is executed with specific parameters, such as vCenter Server details, domain information, and LDAPS URLs for primary and secondary servers.
Configure-VcIdentitySourceLdaps -vcenter "vc01.lab.lan" -vcenter_username "[email protected]" -vcenter_password "VMware1!" -base_user_dn "dc=lab,dc=lan" -base_group_dn "dc=lab,dc=lan" -vcenter_root_password "VMware1!" -domain "lab.lan" -domain_user "[email protected]" -domain_password "VMware1!" -primary_server_url "ldaps://ldc01.lab.lan:636" -secondary_server_url "ldaps://ldc02.lab.lan:636"
Download the Script :
To access and download the Configure-VcIdentitySourceLdaps.ps1 script, visit my GitHub repository at vkernel/vmware-scripts.