Added Icinga Agent management Cmdlets

This commit is contained in:
Lord Hepipud 2019-09-29 18:25:40 +02:00
parent 63a2054aa3
commit 25dc0031b0
32 changed files with 988 additions and 0 deletions

View file

@ -0,0 +1,6 @@
function Get-IcingaAgentArchitecture()
{
$IcingaAgent = Get-IcingaAgentInstallation;
return $IcingaAgent.Architecture;
}

View file

@ -0,0 +1,11 @@
function Get-IcingaAgentBinary()
{
$IcingaRootDir = Get-IcingaAgentRootDirectory;
$IcingaBinary = (Join-Path -Path $IcingaRootDir -ChildPath '\sbin\icinga2.exe');
if ((Test-Path $IcingaBinary) -eq $FALSE) {
throw 'Icinga Agent binary could not be found';
}
return $IcingaBinary;
}

View file

@ -0,0 +1,4 @@
function Get-IcingaAgentConfigDirectory()
{
return (Join-Path -Path $Env:ProgramData -ChildPath 'icinga2\etc\icinga2\')
}

View file

@ -0,0 +1,20 @@
function Get-IcingaAgentFeatures()
{
$Binary = Get-IcingaAgentBinary;
$ConfigResult = Start-IcingaProcess -Executable $Binary -Arguments 'feature list';
$DisabledFeatures = ($ConfigResult.Message.SubString(
0,
$ConfigResult.Message.IndexOf('Enabled features')
)).Replace('Disabled features: ', '').Replace("`r`n", '');
$EnabledFeatures = ($ConfigResult.Message.SubString(
$ConfigResult.Message.IndexOf('Enabled features'),
$ConfigResult.Message.Length - $ConfigResult.Message.IndexOf('Enabled features')
)).Replace('Enabled features: ', '').Replace("`r`n", '');
return @{
'Enabled' = ($EnabledFeatures.Split(' '));
'Disabled' = ($DisabledFeatures.Split(' '));
}
}

View file

@ -0,0 +1,40 @@
function Get-IcingaAgentInstallation()
{
[string]$architecture = '';
if ([IntPtr]::Size -eq 4) {
$architecture = "x86";
$regPath = 'HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall\*';
} else {
$architecture = "x86_64";
$regPath = @('HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall\*', 'HKLM:\Software\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall\*');
}
$RegistryData = Get-ItemProperty $regPath;
$IcingaData = $null;
foreach ($entry in $RegistryData) {
if ($entry.DisplayName -eq 'Icinga 2') {
$IcingaData = $entry;
break;
}
}
if ($null -eq $IcingaData) {
return @{
'Installed' = $FALSE;
'RootDir' = '';
'Version' = (Split-IcingaVersion);
'Architecture' = $architecture;
'Uninstaller' = '';
'InstallDate' = '';
};
}
return @{
'Installed' = $TRUE;
'RootDir' = $IcingaData.InstallLocation;
'Version' = (Split-IcingaVersion $IcingaData.DisplayVersion);
'Architecture' = $architecture;
'Uninstaller' = $IcingaData.UninstallString.Replace("MsiExec.exe ", "");
'InstallDate' = $IcingaData.InstallDate;
};
}

View file

@ -0,0 +1,4 @@
function Get-IcingaAgentLogDirectory()
{
return (Join-Path -Path $Env:ProgramData -ChildPath 'icinga2\var\log\icinga2\')
}

View file

@ -0,0 +1,73 @@
function Get-IcingaAgentMSIPackage()
{
param(
[string]$Source,
[string]$Version,
[switch]$SkipDownload
);
if ([string]::IsNullOrEmpty($Version)) {
throw 'Please specify a valid version: "snapshot", "latest" or a specific version like "2.11.0"';
}
if ([string]::IsNullOrEmpty($Source)) {
throw 'Please specify a valid download URL, like "https://packages.icinga.com/windows/"';
}
# Disable the progress bar for the WebRequest
$ProgressPreference = "SilentlyContinue";
$Architecture = Get-IcingaAgentArchitecture;
$LastUpdate = $null;
if ($Version -eq 'snapshot' -Or $Version -eq 'latest') {
$Content = (Invoke-WebRequest -Uri $Source -UseBasicParsing).RawContent.Split("`r`n");
$UsePackage = $null;
foreach ($line in $Content) {
if ($line -like '*.msi*' -And $line -like "*$Architecture*") {
#Write-Host '#####' $line
$MSIPackage = $line.SubString(
$line.IndexOf('Icinga2-'),
$line.IndexOf('.msi') - $line.IndexOf('Icinga2-')
);
$LastUpdate = $line.SubString(
$line.IndexOf('indexcollastmod">') + 17,
$line.Length - $line.IndexOf('indexcollastmod">') - 17
);
$LastUpdate = $LastUpdate.SubString(0, $LastUpdate.IndexOf(' '));
$LastUpdate = $LastUpdate.Replace('-', '');
$MSIPackage = [string]::Format('{0}.msi', $MSIPackage);
if ($Version -eq 'snapshot') {
if ($line -like '*snapshot*') {
$UsePackage = $MSIPackage;
break;
}
} elseif ($Version -eq 'latest') {
if ($line -like '*snapshot*') {
continue;
}
$UsePackage = $MSIPackage;
break;
}
}
}
} else {
$UsePackage = [string]::Format('Icinga2-v{0}-{1}.msi', $Version, $Architecture);
}
if ($null -eq $UsePackage) {
throw 'No Icinga installation MSI package for your architecture could be found for the provided version and source';
}
if ($SkipDownload -eq $FALSE) {
$DownloadPath = Join-Path $Env:TEMP -ChildPath $UsePackage;
Write-Host ([string]::Format('Download Icinga 2 Agent installer "{0}" into temp directory "{1}"', $UsePackage, $DownloadPath));
Invoke-WebRequest -Uri ([string]::Format('{0}/{1}', $Source, $UsePackage)) -OutFile $DownloadPath;
}
return @{
'InstallerPath' = $DownloadPath;
'Version' = ($UsePackage).Replace('Icinga2-v', '').Replace($Architecture, '').Replace('.msi', '').Replace('-', '');
'LastUpdate' = $LastUpdate;
}
}

View file

@ -0,0 +1,9 @@
function Get-IcingaAgentRootDirectory()
{
$IcingaAgent = Get-IcingaAgentInstallation;
if ($IcingaAgent.Installed -eq $FALSE) {
return '';
}
return $IcingaAgent.RootDir;
}

View file

@ -0,0 +1,6 @@
function Get-IcingaAgentVersion()
{
$IcingaAgent = Get-IcingaAgentInstallation;
return $IcingaAgent.Version;
}

View file

@ -0,0 +1,27 @@
function Get-IcingaHostname()
{
param(
[string]$Hostname,
[bool]$AutoUseFQDN = $FALSE,
[bool]$AutoUseHostname = $FALSE,
[bool]$UpperCase = $FALSE,
[bool]$LowerCase = $FALSE
);
[string]$UseHostname = '';
if ([string]::IsNullOrEmpty($Hostname) -eq $FALSE) {
$UseHostname = $Hostname;
} elseif ($AutoUseFQDN) {
$UseHostname = [System.Net.Dns]::GetHostEntry("localhost").HostName;
} else {
$UseHostname = [System.Net.Dns]::GetHostName();
}
if ($UpperCase) {
$UseHostname = $UseHostname.ToUpper();
} elseif ($LowerCase) {
$UseHostname = $UseHostname.ToLower();
}
return $UseHostname;
}

View file

@ -0,0 +1,11 @@
function Get-IcingaServiceUser()
{
$Services = Get-IcingaServices -Service 'icinga2';
if ($null -eq $Services) {
throw 'Icinga Service not installed';
}
$Services = $Services.GetEnumerator() | Select-Object -First 1;
return ($Services.Value.configuration.ServiceUser).Replace('.\', '');
}

View file

@ -0,0 +1,78 @@
function Install-IcingaAgent()
{
param(
[string]$Version,
[string]$Source = 'https://packages.icinga.com/windows/',
[string]$InstallDir = '',
[switch]$AllowUpdates
);
$IcingaData = Get-IcingaAgentInstallation;
$InstalledVersion = Get-IcingaAgentVersion;
$IcingaInstaller = Get-IcingaAgentMSIPackage -Source $Source -Version $Version -SkipDownload;
$InstallTarget = $IcingaData.RootDir;
if ($IcingaData.Installed -eq $TRUE -and $AllowUpdates -eq $FALSE) {
Write-Host 'The Icinga Agent is already installed on this system. To perform updates or downgrades, please add the "-AllowUpdates" argument';
return $FALSE;
}
if ($Version -eq 'snapshot') {
if ($IcingaData.InstallDate -ge $IcingaInstaller.LastUpdate -And [string]::IsNullOrEmpty($InstalledVersion.Snapshot) -eq $FALSE) {
Write-Host 'There is no new snapshot package available which requires to be installed.'
return $FALSE;
}
$IcingaInstaller.Version = 'snapshot';
} elseif ($IcingaInstaller.Version -eq $InstalledVersion.Full) {
Write-Host ([string]::Format(
'No installation required. Your installed version [{0}] is matching the online version [{1}]',
$InstalledVersion.Full,
$IcingaInstaller.Version
));
return $FALSE;
}
$IcingaInstaller = Get-IcingaAgentMSIPackage -Source $Source -Version $IcingaInstaller.Version;
if ((Test-Path $IcingaInstaller.InstallerPath) -eq $FALSE) {
throw 'Failed to locate Icinga Agent installer file';
}
if ([string]::IsNullOrEmpty($InstallDir) -eq $FALSE) {
if ((Test-Path $InstallDir) -eq $FALSE) {
New-Item -Path $InstallDir -Force | Out-Null;
$InstallTarget = $InstallDir;
}
}
[string]$InstallFolderMsg = $InstallTarget;
if ([string]::IsNullOrEmpty($InstallTarget) -eq $FALSE) {
$InstallTarget = [string]::Format(' INSTALL_ROOT="{0}"', $InstallTarget);
} else {
$InstallTarget = '';
if ($IcingaData.Architecture -eq 'x86') {
$InstallFolderMsg = Join-Path -Path ${env:ProgramFiles(x86)} -ChildPath 'ICINGA2';
} else {
$InstallFolderMsg = Join-Path -Path $env:ProgramFiles -ChildPath 'ICINGA2';
}
}
Write-Host ([string]::Format('Installing new Icinga Agent version into "{0}"', $InstallFolderMsg));
if ($IcingaData.Installed) {
if ((Uninstall-IcingaAgent) -eq $FALSE) {
return $FALSE;
}
}
$InstallProcess = Start-IcingaProcess -Executable 'MsiExec.exe' -Arguments ([string]::Format('/quiet /i "{0}" {1}', $IcingaInstaller.InstallerPath, $InstallTarget)) -FlushNewLines;
if ($InstallProcess.ExitCode -ne 0) {
Write-Host ([string]::Format('Failed to install Icinga 2 Agent: {0}{1}', $InstallProcess.Message, $InstallProcess.Error));
return $FALSE;
}
Write-Host 'Icinga Agent was successfully installed';
return $TRUE;
}

View file

@ -0,0 +1,5 @@
function Install-IcingaAgentBaseFeatures()
{
Disable-IcingaAgentFeature -Feature 'checker';
Enable-IcingaAgentFeature -Feature 'api';
}

View file

@ -0,0 +1,224 @@
function Install-IcingaAgentCertificates()
{
param(
[string]$Hostname,
[string]$Endpoint,
[int]$Port = 5665,
[string]$CACert,
[string]$Ticket,
[switch]$Force = $FALSE
);
if ([string]::IsNullOrEmpty($Hostname)) {
throw 'Failed to install Icinga Agent certificates. Please provide a hostname';
}
# Default for Icinga 2.8.0 and above
[string]$NewCertificateDirectory = (Join-Path -Path $Env:ProgramData -ChildPath 'icinga2\var\lib\icinga2\certs\');
[string]$OldCertificateDirectory = (Join-Path -Path $Env:ProgramData -ChildPath 'icinga2\etc\icinga2\pki\');
[string]$CertificateDirectory = $NewCertificateDirectory;
if ((Compare-IcingaVersions -RequiredVersion '2.8.0') -eq $FALSE) {
# Certificate path for versions older than 2.8.0
$CertificateDirectory = $OldCertificateDirectory;
Move-IcingaAgentCertificates -Source $NewCertificateDirectory -Destination $OldCertificateDirectory;
} else {
Move-IcingaAgentCertificates -Source $OldCertificateDirectory -Destination $NewCertificateDirectory;
}
if (-Not (Test-IcingaAgentCertificates -CertDirectory $CertificateDirectory -Hostname $Hostname -Force $Force)) {
Write-Host ([string]::Format('Generating host certificates for host "{0}"', $Hostname));
$arguments = [string]::Format('pki new-cert --cn {0} --key {1}{0}.key --cert {1}{0}.crt',
$Hostname,
$CertificateDirectory
);
if ((Start-IcingaAgentCertificateProcess -Arguments $arguments) -eq $FALSE) {
throw 'Failed to generate host certificate';
}
}
if ([string]::IsNullOrEmpty($Endpoint) -And [string]::IsNullOrEmpty($CACert)) {
Write-Host 'Your host certificates have been generated successfully. Please either specify an endpoint to connect to or provide the path to a valid ca.crt.';
return $TRUE;
}
if (-Not [string]::IsNullOrEmpty($Endpoint)) {
if (-Not (Test-IcingaAgentCertificates -CertDirectory $CertificateDirectory -Hostname $Hostname -TestTrustedParent -Force $Force)) {
Write-Host ([string]::Format('Fetching trusted master certificate from "{0}"', $Endpoint));
$arguments = [string]::Format('pki save-cert --key {0}{1}.key --trustedcert {0}trusted-parent.crt --host {2}',
$CertificateDirectory,
$Hostname,
$Endpoint
);
if ((Start-IcingaAgentCertificateProcess -Arguments $arguments) -eq $FALSE) {
Write-Host 'Unable to connect to your provided Icinga CA. Please verify the entered configuration is correct.' `
'If you are not able to connect to your Icinga CA from this machine, you will have to provide the path' `
'to your Icinga ca.crt and use the CA-Proxy certificate handling.';
return $TRUE;
}
}
if (-Not (Test-IcingaAgentCertificates -CertDirectory $CertificateDirectory -Hostname $Hostname -TestCACert -Force $Force)) {
[string]$PKIRequest = 'pki request --host {0} --port {1} --ticket {4} --key {2}{3}.key --cert {2}{3}.crt --trustedcert {2}trusted-parent.crt --ca {2}ca.crt';
if ([string]::IsNullOrEmpty($Ticket)) {
$PKIRequest = 'pki request --host {0} --port {1} --key {2}{3}.key --cert {2}{3}.crt --trustedcert {2}trusted-parent.crt --ca {2}ca.crt';
}
$arguments = [string]::Format($PKIRequest,
$Endpoint,
$Port,
$CertificateDirectory,
$Hostname,
$Ticket
);
if ((Start-IcingaAgentCertificateProcess -Arguments $arguments) -eq $FALSE) {
throw 'Failed to sign Icinga certificate';
}
if ([string]::IsNullOrEmpty($Ticket)) {
Write-Host 'Your certificates were generated successfully. Please sign the certificate now on your Icinga CA master. You can lookup open requests with "icinga2 ca list"';
} else {
Write-Host 'Icinga certificates successfully installed';
}
}
return $TRUE;
} elseif (-Not [string]::IsNullOrEmpty($CACert)) {
if (-Not (Copy-IcingaAgentCACertificate -CAPath $CACert -Desination $CertificateDirectory)) {
return $FALSE;
}
Write-Host 'Host-Certificates and ca.crt are present. Please start your Icinga Agent now and manually sign your certificate request on your CA master. You can lookup open requests with "icinga2 ca list"';
}
return $TRUE;
}
function Start-IcingaAgentCertificateProcess()
{
param(
$Arguments
);
$Binary = Get-IcingaAgentBinary;
$Process = Start-IcingaProcess -Executable $Binary -Arguments $Arguments;
if ($Process.ExitCode -ne 0) {
Write-Host ([string]::Format('Failed to create certificate.{0}Arguments: {1}{0}Error:{2} {3}', "`r`n", $Arguments, $Process.Message, $Process.Error));
return $FALSE;
}
Write-Host $Process.Message;
return $TRUE;
}
function Move-IcingaAgentCertificates()
{
param(
[string]$Source,
[string]$Destination
);
$SourceDir = Join-Path -Path $Source -ChildPath '\*';
$TargetDir = Join-Path -Path $Destination -ChildPath '\';
Move-Item -Path $SourceDir -Destination $TargetDir;
}
function Test-IcingaAgentCertificates()
{
param(
[string]$CertDirectory,
[string]$Hostname,
[switch]$TestCACert,
[switch]$TestTrustedParent,
[bool]$Force
);
if ($Force) {
return $FALSE;
}
if ($TestCACert) {
if (Test-Path (Join-Path -Path $CertDirectory -ChildPath 'ca.crt')) {
Write-Host 'Your ca.crt is present. No generation or fetching required';
return $TRUE;
} else {
Write-Host 'Your ca.crt is not present. Manuall copy or fetching from your Icinga CA is required.';
return $FALSE;
}
}
if ($TestTrustedParent) {
if (Test-Path (Join-Path -Path $CertDirectory -ChildPath 'trusted-parent.crt')) {
Write-Host 'Your trusted-parent.crt is present. No fetching or generation required';
return $TRUE;
} else {
Write-Host 'Your trusted master certificate is not present. Fetching from your CA server is required';
return $FALSE;
}
}
if ((-Not (Test-Path ((Join-Path -Path $CertDirectory -ChildPath $Hostname) + '.key'))) `
-Or -Not (Test-Path ((Join-Path -Path $CertDirectory -ChildPath $Hostname) + '.crt'))) {
return $FALSE;
}
[string]$hostCRT = [string]::Format('{0}.crt', $Hostname);
[string]$hostKEY = [string]::Format('{0}.key', $Hostname);
$certificates = Get-ChildItem -Path $CertDirectory;
# Now loop each file and match their name with our hostname
foreach ($cert in $certificates) {
if ($cert.Name.toLower() -eq $hostCRT.toLower() -Or $cert.Name.toLower() -eq $hostKEY.toLower()) {
$file = $cert.Name.Replace('.key', '').Replace('.crt', '');
if (-Not ($file -clike $Hostname)) {
Write-Host ([string]::Format('Certificate file {0} is not matching the hostname {1}. Certificate generation is required.', $cert.Name, $Hostname));
return $FALSE;
}
}
}
Write-Host 'Icinga host certificates are present and valid. No generation required.';
return $TRUE;
}
function Copy-IcingaAgentCACertificate()
{
param(
[string]$CAPath,
[string]$Desination
);
# Copy ca.crt from local path or network share to certificate path
if ((Test-Path $CAPath)) {
Copy-Item -Path $CAPath -Destination (Join-Path -Path $Desination -ChildPath 'ca.crt') | Out-Null;
Write-Host ([string]::Format('Copied ca.crt from "{0}" to "{1}', $CAPath, $Desination));
} else {
# It could also be a web ressource
try {
$response = Invoke-WebRequest $CAPath -UseBasicParsing;
[int]$Index = $response.RawContent.IndexOf("`r`n`r`n") + 4;
[string]$CAContent = $response.RawContent.SubString(
$Index,
$response.RawContent.Length - $Index
);
Set-Content -Path (Join-Path $Desination -ChildPath 'ca.crt') -Value $CAContent;
Write-Host ([string]::Format('Downloaded ca.crt from "{0}" to "{1}', $CAPath, $Desination))
} catch {
Write-Host 'Failed to load any provided ca.crt ressource';
return $FALSE;
}
}
return $TRUE;
}
Export-ModuleMember -Function @('Install-IcingaAgentCertificates');

View file

@ -0,0 +1,21 @@
function Uninstall-IcingaAgent()
{
$IcingaData = Get-IcingaAgentInstallation;
if ($IcingaData.Installed -eq $FALSE) {
Write-Host 'Unable to uninstall the Icinga Agent. The Agent is not installed';
return;
}
Write-Host 'Removing current installed Icinga Agent';
$Uninstaller = Start-IcingaProcess -Executable 'MsiExec.exe' -Arguments ([string]::Format('{0} /q', $IcingaData.Uninstaller)) -FlushNewLine;
if ($Uninstaller.ExitCode -ne 0) {
Write-Host ([string]::Format('Failed to remove Icinga 2 Agent: {0}{1}', $Uninstaller.Message, $Uninstaller.Error));
return $FALSE;
}
Write-Host 'Icinga Agent was successfully removed';
return $TRUE;
}

View file

@ -0,0 +1,33 @@
function Compare-IcingaVersions()
{
param(
$CurrentVersion,
$RequiredVersion
);
if ([string]::IsNullOrEmpty($RequiredVersion)) {
return $FALSE;
}
$RequiredVersion = Split-IcingaVersion -Version $RequiredVersion;
if ([string]::IsNullOrEmpty($CurrentVersion) -eq $FALSE) {
$CurrentVersion = Split-IcingaVersion -Version $CurrentVersion;
} else {
$CurrentVersion = Get-IcingaAgentVersion;
}
if ($requiredVersion.Mayor -gt $currentVersion.Mayor) {
return $FALSE;
}
if ($requiredVersion.Minor -gt $currentVersion.Minor) {
return $FALSE;
}
if ($requiredVersion.Minor -ge $currentVersion.Minor -And $requiredVersion.Fixes -gt $currentVersion.Fixes) {
return $FALSE;
}
return $TRUE;
}

View file

@ -0,0 +1,24 @@
function Disable-IcingaAgentFeature()
{
param(
[string]$Feature
);
if ([string]::IsNullOrEmpty($Feature)) {
throw 'Please specify a valid feature';
}
if ((Test-IcingaAgentFeatureEnabled -Feature $Feature) -eq $FALSE) {
Write-Host 'This feature is already disabled.'
return;
}
$Binary = Get-IcingaAGentBinary;
$Process = Start-IcingaProcess -Executable $Binary -Arguments ([string]::Format('feature disable {0}', $Feature));
if ($Process.ExitCode -ne 0) {
throw ([string]::Format('Failed to disable Icinga Feature: {0}', $Process.Message));
}
Write-Host ([string]::Format('Feature "{0}" was successfully disabled', $Feature));
}

View file

@ -0,0 +1,24 @@
function Enable-IcingaAgentFeature()
{
param(
[string]$Feature
);
if ([string]::IsNullOrEmpty($Feature)) {
throw 'Please specify a valid feature';
}
if ((Test-IcingaAgentFeatureEnabled -Feature $Feature)) {
Write-Host 'This feature is already enabled.'
return;
}
$Binary = Get-IcingaAGentBinary;
$Process = Start-IcingaProcess -Executable $Binary -Arguments ([string]::Format('feature enable {0}', $Feature));
if ($Process.ExitCode -ne 0) {
throw ([string]::Format('Failed to enable Icinga Feature: {0}', $Process.Message));
}
Write-Host ([string]::Format('Feature "{0}" was successfully enabled', $Feature));
}

View file

@ -0,0 +1,23 @@
function Move-IcingaAgentDefaultConfig()
{
$ConfigDir = Get-IcingaAgentConfigDirectory;
$BackupFile = Join-Path -Path $ConfigDir -ChildPath 'ps_backup\backup_executed.key';
if ((Test-Path $BackupFile)) {
Write-Host 'A backup of your default configuration is not required. A backup was already made.';
return;
}
New-Item (Join-Path -Path $ConfigDir -ChildPath 'ps_backup') -ItemType Directory | Out-Null;
Move-Item -Path (Join-Path -Path $ConfigDir -ChildPath 'conf.d') -Destination (Join-Path -Path $ConfigDir -ChildPath 'ps_backup\conf.d');
Move-Item -Path (Join-Path -Path $ConfigDir -ChildPath 'zones.conf') -Destination (Join-Path -Path $ConfigDir -ChildPath 'ps_backup\zones.conf');
Copy-Item -Path (Join-Path -Path $ConfigDir -ChildPath 'constants.conf') -Destination (Join-Path -Path $ConfigDir -ChildPath 'ps_backup\constants.conf');
Copy-Item -Path (Join-Path -Path $ConfigDir -ChildPath 'features-available') -Destination (Join-Path -Path $ConfigDir -ChildPath 'ps_backup\features-available');
New-Item (Join-Path -Path $ConfigDir -ChildPath 'conf.d') -ItemType Directory | Out-Null;
New-Item (Join-Path -Path $ConfigDir -ChildPath 'zones.conf') -ItemType File | Out-Null;
New-Item -Path $BackupFile -ItemType File | Out-Null;
Write-Host 'Successfully backed up Icinga 2 Agent default config';
}

View file

@ -0,0 +1,12 @@
function Show-IcingaAgentObjects()
{
$Binary = Get-IcingaAgentBinary;
$Output = Start-IcingaProcess -Executable $Binary -Arguments 'object list';
if ($Output.ExitCode -ne 0) {
Write-Host ([string]::Format('Failed to fetch Icinga Agent objects list: {0}{1}', $Output.Message, $Output.Error));
return $null;
}
return $Output.Message;
}

View file

@ -0,0 +1,31 @@
function Split-IcingaVersion()
{
param(
[string]$Version
);
if ([string]::IsNullOrEmpty($Version)) {
return @{
'Full' = '';
'Mayor' = $null;
'Minor' = $null;
'Fixes' = $null;
'Snapshot' = $null;
}
}
[array]$IcingaVersion = $Version.Split('.');
$Snapshot = $null;
if ([string]::IsNullOrEmpty($IcingaVersion[3]) -eq $FALSE) {
$Snapshot = [int]$IcingaVersion[3];
}
return @{
'Full' = $Version;
'Mayor' = [int]$IcingaVersion[0];
'Minor' = [int]$IcingaVersion[1];
'Fixes' = [int]$IcingaVersion[2];
'Snapshot' = $Snapshot;
}
}

View file

@ -0,0 +1,10 @@
function Read-IcingaAgentDebugLogFile()
{
$Logfile = Join-Path -Path (Get-IcingaAgentLogDirectory) -ChildPath 'debug.log';
if ((Test-Path $Logfile) -eq $FALSE) {
Write-Host 'Icinga 2 debug logfile not present. Unable to load it';
return;
}
Get-Content -Path $Logfile -Wait;
}

View file

@ -0,0 +1,10 @@
function Read-IcingaAgentLogFile()
{
$Logfile = Join-Path -Path (Get-IcingaAgentLogDirectory) -ChildPath 'icinga2.log';
if ((Test-Path $Logfile) -eq $FALSE) {
Write-Host 'Icinga 2 logfile not present. Unable to load it';
return;
}
Get-Content -Path $Logfile -Wait;
}

View file

@ -0,0 +1,24 @@
function Set-IcingaAcl()
{
param(
[string]$Directory
);
if (-Not (Test-Path $Directory)) {
throw 'Failed to set Acl for directory. Directory does not exist';
return;
}
$DirectoryAcl = Get-Acl -Path $Directory;
$DirectoryAccessRule = New-Object System.Security.AccessControl.FileSystemAccessRule(
(Get-IcingaServiceUser),
'Modify',
'ContainerInherit,ObjectInherit',
'None',
'Allow'
);
$DirectoryAcl.SetAccessRule($DirectoryAccessRule);
Set-Acl -Path $Directory -AclObject $DirectoryAcl;
Test-IcingaAcl -Directory $Directory -WriteOutput | Out-Null;
}

View file

@ -0,0 +1,35 @@
function Set-IcingaAgentNodeName()
{
param(
$Hostname
);
if ([string]::IsNullOrEmpty($Hostname)) {
throw 'You have to specify a hostname in order to change the Icinga Agent NodeName';
}
$ConfigDir = Get-IcingaAgentConfigDirectory;
$ConstantsConf = Join-Path -Path $ConfigDir -ChildPath 'constants.conf';
$ConfigContent = Get-Content -Path $ConstantsConf;
if ($ConfigContent.Contains('//const NodeName = "localhost"')) {
$ConfigContent = $ConfigContent.Replace(
'//const NodeName = "localhost"',
[string]::Format('const NodeName = "{0}"', $Hostname)
);
} else {
[string]$NewConfigContent = '';
foreach ($line in $ConfigContent) {
if ($line.Contains('const NodeName =')) {
$line = [string]::Format('const NodeName = "{0}"', $Hostname);
}
$NewConfigContent = [string]::Format('{0}{1}{2}', $NewConfigContent, $line, "`r`n");
}
$ConfigContent = $NewConfigContent;
}
Set-Content -Path $ConstantsConf -Value $ConfigContent;
Write-Host ([string]::Format('Your hostname was successfully changed to "{0}"', $Hostname));
}

View file

@ -0,0 +1,45 @@
function Test-IcingaAcl()
{
param(
[string]$Directory,
[switch]$WriteOutput
);
if (-Not (Test-Path $Directory)) {
throw 'The specified directory was not found';
}
$FolderACL = Get-Acl $Directory;
$ServiceUser = Get-IcingaServiceUser;
$UserFound = $FALSE;
$HasAccess = $FALSE;
foreach ($user in $FolderACL.Access) {
# Not only check here for the exact name but also for included strings like NT AU or NT-AU or even further later on
# As the Get-Acl Cmdlet will translate usernames into the own language, resultng in 'NT AUTHORITY\NetworkService' being translated
# to 'NT-AUTORITÄT\Netzwerkdienst' for example
if ($user.IdentityReference -like "*$ServiceUser" -Or ($ServiceUser -Like '*NT AU*' -And ($user.IdentityReference -Like '*NT AU*' -Or $user.IdentityReference -Like '*NT-AU*'))) {
$UserFound = $TRUE;
if ($user.FileSystemRights -Like '*Modify*' -And $user.FileSystemRights -Like '*Synchronize*') {
$HasAccess = $TRUE;
}
}
}
if ($WriteOutput) {
[string]$messageFormat = 'Directory "{0}" {1} by the Icinga Service User "{2}"';
if ($UserFound) {
if ($HasAccess) {
Write-IcingaTestOutput -Severity 'PASSED' -Message ([string]::Format($messageFormat, $Directory, 'is accessable and writeable', $ServiceUser));
} else {
Write-IcingaTestOutput -Severity 'FAILED' -Message ([string]::Format($messageFormat, $Directory, 'is accessable but NOT writeable', $ServiceUser));
Write-Host "\_ Please run the following command to fix this issue: Set-IcingaAcl -Directory '$Directory'";
}
} else {
Write-IcingaTestOutput -Severity 'FAILED' -Message ([string]::Format($messageFormat, $Directory, 'is not accessable', $ServiceUser));
Write-Host "\_ Please run the following command to fix this issue: Set-IcingaAcl -Directory '$Directory'";
}
}
return $UserFound;
}

View file

@ -0,0 +1,17 @@
function Test-IcingaAgent()
{
if (Get-Service 'icinga2' -ErrorAction SilentlyContinue) {
Write-IcingaTestOutput -Severity 'PASSED' -Message 'Icinga Agent Service is installed';
Test-IcingaAcl "$Env:ProgramData\icinga2\etc" -WriteOutput | Out-Null;
Test-IcingaAcl "$Env:ProgramData\icinga2\var" -WriteOutput | Out-Null;
Test-IcingaAcl (Get-IcingaCacheDir) -WriteOutput | Out-Null;
Test-IcingaAgentConfig | Out-Null;
if (Test-IcingaAgentFeatureEnabled -Feature 'debuglog') {
Write-IcingaTestOutput -Severity 'WARNING' -Message 'The Debug-Log of the Icinga Agent is enabled. Please keep in mind to disable it once testing is done, as a huge amount of data is generated.'
} else {
Write-IcingaTestOutput -Severity 'PASSED' -Message 'Icinga Agent Debug-Log is disabled.'
}
} else {
Write-IcingaTestOutput -Severity 'FAILED' -Message 'Icinga Agent Service is not installed';
}
}

View file

@ -0,0 +1,20 @@
function Test-IcingaAgentConfig()
{
param (
[switch]$WriteStackTrace
);
$Binary = Get-IcingaAgentBinary;
$ConfigResult = Start-IcingaProcess -Executable $Binary -Arguments 'daemon -C';
if ($ConfigResult.ExitCode -eq 0) {
Write-IcingaTestOutput -Severity 'PASSED' -Message 'Icinga Agent configuration is valid';
return $TRUE;
} else {
Write-IcingaTestOutput -Severity 'FAILED' -Message 'Icinga Agent configuration is containing errors. Run this command for getting a detailed error report: "Test-IcingaAgentConfig -WriteStackTrace | Out-Null"';
if ($WriteStackTrace) {
Write-Host $ConfigResult.Message;
}
return $FALSE;
}
}

View file

@ -0,0 +1,14 @@
function Test-IcingaAgentFeatureEnabled()
{
param(
[string]$Feature
);
$Features = Get-IcingaAgentFeatures;
if ($Features.Enabled -Contains $Feature) {
return $TRUE;
}
return $FALSE;
}

View file

@ -0,0 +1,20 @@
function Write-IcingaAgentApiConfig()
{
param(
[int]$Port = 5665
);
[string]$ApiConf = '';
$ApiConf = [string]::Format('{0}object ApiListener "api" {1}{2}', $ApiConf, '{', "`r`n");
$ApiConf = [string]::Format('{0} accept_commands = true;{1}', $ApiConf, "`r`n");
$ApiConf = [string]::Format('{0} accept_config = true;{1}', $ApiConf, "`r`n");
$ApiConf = [string]::Format('{0} bind_host = "::";{1}', $ApiConf, "`r`n");
$ApiConf = [string]::Format('{0} bind_port = {1};{2}', $ApiConf, $Port, "`r`n");
$ApiConf = [string]::Format('{0}{1}{2}{2}', $ApiConf, '}', "`r`n");
$ApiConf = $ApiConf.Substring(0, $ApiConf.Length - 4);
Set-Content -Path (Join-Path -Path (Get-IcingaAgentConfigDirectory) -ChildPath 'features-available\api.conf') -Value $ApiConf;
Write-Host 'Api configuration has been written successfully';
}

View file

@ -0,0 +1,78 @@
function Write-IcingaAgentZonesConfig()
{
param(
[array]$Endpoints = @(),
[array]$EndpointConnections = @(),
[string]$ParentZone = '',
[array]$GlobalZones = @(),
[string]$Hostname = ''
);
if ($Endpoints.Count -eq 0) {
throw 'Please properly specify your endpoint names';
}
if ([string]::IsNullOrEmpty($ParentZone)) {
throw 'Please specify a parent zone this agent shall connect to / receives connections from';
}
if ([string]::IsNullOrEmpty($Hostname)) {
throw 'Please specify hostname for this agent configuration';
}
[int]$Index = 0;
[string]$ZonesConf = '';
$ZonesConf = [string]::Format('{0}object Endpoint "{1}" {2}{3}', $ZonesConf, $Hostname, '{', "`r`n");
$ZonesConf = [string]::Format('{0}{1}{2}{2}', $ZonesConf, '}', "`r`n");
foreach ($endpoint in $Endpoints) {
$ZonesConf = [string]::Format('{0}object Endpoint "{1}" {2}{3}', $ZonesConf, $endpoint, '{', "`r`n");
if ($EndpointConnections.Count -ne 0) {
$ConnectionConfig = Get-IPConfigFromString -IPConfig ($EndpointConnections[$Index]);
$ZonesConf = [string]::Format('{0} host = "{1}";{2}', $ZonesConf, $ConnectionConfig.address, "`r`n");
if ([string]::IsNullOrEmpty($ConnectionConfig.port) -eq $FALSE) {
$ZonesConf = [string]::Format('{0} port = "{1}";{2}', $ZonesConf, $ConnectionConfig.port, "`r`n");
}
}
$ZonesConf = [string]::Format('{0}{1}{2}{2}', $ZonesConf, '}', "`r`n");
$Index += 1;
}
[string]$EndpointString = '';
foreach ($endpoint in $Endpoints) {
$EndpointString = [string]::Format(
'{0}"{1}", ',
$EndpointString,
$endpoint
);
}
$EndpointString = $EndpointString.Substring(0, $EndpointString.Length - 2);
$ZonesConf = [string]::Format('{0}object Zone "{1}" {2}{3}', $ZonesConf, $ParentZone, '{', "`r`n");
$ZonesConf = [string]::Format('{0} endpoints = [ {1} ];{2}', $ZonesConf, $EndpointString, "`r`n");
$ZonesConf = [string]::Format('{0}{1}{2}{2}', $ZonesConf, '}', "`r`n");
$ZonesConf = [string]::Format('{0}object Zone "{1}" {2}{3}', $ZonesConf, $Hostname, '{', "`r`n");
$ZonesConf = [string]::Format('{0} parent = "{1}";{2}', $ZonesConf, $ParentZone, "`r`n");
$ZonesConf = [string]::Format('{0} endpoints = [ "{1}" ];{2}', $ZonesConf, $Hostname, "`r`n");
$ZonesConf = [string]::Format('{0}{1}{2}{2}', $ZonesConf, '}', "`r`n");
if ($GlobalZones.Contains('director-global') -eq $FALSE) {
$GlobalZones += 'director-global';
}
if ($GlobalZones.Contains('global-templates') -eq $FALSE) {
$GlobalZones += 'global-templates';
}
foreach ($zone in $GlobalZones) {
$ZonesConf = [string]::Format('{0}object Zone "{1}" {2}{3}', $ZonesConf, $zone, '{', "`r`n");
$ZonesConf = [string]::Format('{0} global = true;{1}', $ZonesConf, "`r`n");
$ZonesConf = [string]::Format('{0}{1}{2}{2}', $ZonesConf, '}', "`r`n");
}
$ZonesConf = $ZonesConf.Substring(0, $ZonesConf.Length - 4);
Set-Content -Path (Join-Path -Path (Get-IcingaAgentConfigDirectory) -ChildPath 'zones.conf') -Value $ZonesConf;
Write-Host 'Icinga Agent zones.conf has been written successfully';
}

View file

@ -0,0 +1,29 @@
function Write-IcingaTestOutput()
{
param(
[ValidateSet('PASSED', 'WARNING', 'FAILED')]
$Severity,
$Message
);
$Color = 'Green';
Switch ($Severity) {
'PASSED' {
$Color = 'Green';
break;
};
'WARNING' {
$Color = 'Yellow';
break;
};
'FAILED' {
$Color = 'Red';
break;
};
}
Write-Host '[' -NoNewline;
Write-Host $Severity -ForegroundColor $Color -NoNewline;
Write-Host ']:' $Message;
}