au2mator-AD-AddUserToGroup.ps1
<#PSScriptInfo
.VERSION 1.1 .GUID 3da2ef66-500c-4d3e-8e8f-c54f8a8ff3b3 .AUTHOR au2mator .COMPANYNAME au2mator.com .COPYRIGHT .TAGS Windows au2mator ActiveDirectory .LICENSEURI .PROJECTURI https://au2mator.com/add-user-to-group-active-directory-self-service-with-au2mator/ .ICONURI https://au2mator.com/my-content/TransparentPNGsymbol.png .EXTERNALMODULEDEPENDENCIES .REQUIREDSCRIPTS .EXTERNALSCRIPTDEPENDENCIES .RELEASENOTES - Changed Icon #> <# .DESCRIPTION Add an Active Directory User to an Active Directory Group with au2mator Self Service Portal and Azure Automation See the Blog Post https://au2mator.com/add-user-to-group-active-directory-self-service-with-au2mator/ for Preperations like Azure Variables we use. #> ######### # au2mator AA Services # New Service # AD - Add User to Group # v 1.0 Initial Release # Init Release: 03.02.2020 # Last Update: 03.02.2020 # Code Template V 1.1 # URL: https://au2mator.com/add-user-to-group-active-directory-self-service-with-au2mator/ # Github: https://github.com/au2mator/Add-User-to-Group ################# #region InputParamaters ##Question in au2mator param ( [parameter(Mandatory = $true)] [String]$c_User, [parameter(Mandatory = $true)] [String]$c_Group, [parameter(Mandatory = $false)] [String]$c_Comment, ## au2mator Initialize Data [parameter(Mandatory = $true)] [String]$InitiatedBy, [parameter(Mandatory = $true)] [String]$RequestId, [parameter(Mandatory = $true)] [String]$Service, [parameter(Mandatory = $true)] [String]$TargetUserId ) #endregion InputParamaters #region Variables ##Script Handling $DoImportPSSession = $false $ErrorCount = 0 #$ErrorActionPreference = "SilentlyContinue" ## Environment [string]$DCServer = Get-AutomationVariable -Name "au2mator_DC" [string]$LogPath = Get-AutomationVariable -Name "au2mator_LogPath" [string]$LogPath=$LogPath+"AD - Add User to Group" [string]$LogfileName = "Add User to Group" ## au2mator Settings [string]$PortalURL = Get-AutomationVariable -Name "au2mator_PortalURL" [string]$au2matorDBServer = Get-AutomationVariable -Name "au2mator_DBServer" [string]$au2matorDBName = Get-AutomationVariable -Name "au2mator_DBName" ## Control Mail $SendMailToInitiatedByUser = $true #Send a Mail after Service is completed $SendMailToTargetUser = $true #Send Mail to Target User after Service is completed ## SMTP Settings $SMTPServer = Get-AutomationVariable -Name "au2mator_SMTPServer" $cred=Get-AutomationPSCredential -Name 'SMTP_Credentials' $SMTPUser = $cred.UserName $SMTPPassword = $cred.Password $SMPTAuthentication = $true #When True, User and Password needed $EnableSSLforSMTP = $true $SMTPSender = Get-AutomationVariable -Name "au2mator_SMTPSender" #endregion Variab�es #region Functions function ConnectToDB { # define parameters param( [string] $servername, [string] $database ) # create connection and save it as global variable $global:Connection = New-Object System.Data.SQLClient.SQLConnection $Connection.ConnectionString = "server='$servername';database='$database';trusted_connection=false; integrated security='true'" $Connection.Open() Write-Verbose 'Connection established' } # function that executes sql commands against an existing Connection object; In pur case # the connection object is saved by the ConnectToDB function as a global variable function ExecuteSqlQuery { # define parameters param( [string] $sqlquery ) Begin { If (!$Connection) { Throw "No connection to the database detected. Run command ConnectToDB first." } elseif ($Connection.State -eq 'Closed') { Write-Verbose 'Connection to the database is closed. Re-opening connection...' try { # if connection was closed (by an error in the previous script) then try reopen it for this query $Connection.Open() } catch { Write-Verbose "Error re-opening connection. Removing connection variable." Remove-Variable -Scope Global -Name Connection throw "Unable to re-open connection to the database. Please reconnect using the ConnectToDB commandlet. Error is $($_.exception)." } } } Process { #$Command = New-Object System.Data.SQLClient.SQLCommand $command = $Connection.CreateCommand() $command.CommandText = $sqlquery Write-Verbose "Running SQL query '$sqlquery'" try { $result = $command.ExecuteReader() } catch { $Connection.Close() } $Datatable = New-Object "System.Data.Datatable" $Datatable.Load($result) return $Datatable } End { Write-Verbose "Finished running SQL query." } } function Write-au2matorLog { [CmdletBinding()] param ( [ValidateSet('DEBUG', 'INFO', 'WARNING', 'ERROR')] [string]$Type, [string]$Text ) # Set logging path if (!(Test-Path -Path $logPath)) { try { $null = New-Item -Path $logPath -ItemType Directory Write-Verbose ("Path: ""{0}"" was created." -f $logPath) } catch { Write-Verbose ("Path: ""{0}"" couldn't be created." -f $logPath) } } else { Write-Verbose ("Path: ""{0}"" already exists." -f $logPath) } [string]$logFile = '{0}\{1}_{2}.log' -f $logPath, $(Get-Date -Format 'yyyyMMdd'), $LogfileName $logEntry = '{0}: <{1}> <{2}> <{3}> {4}' -f $(Get-Date -Format dd.MM.yyyy-HH:mm:ss), $Type, $RequestId, $Service, $Text Add-Content -Path $logFile -Value $logEntry } function Get-UserInput ($RequestID) { [hashtable]$return = @{ } ConnectToDB -servername $au2matorDBServer -database $au2matorDBName $Result = ExecuteSqlQuery -sqlquery "SELECT RPM.Text AS Question, RP.Value FROM dbo.Requests AS R INNER JOIN dbo.RunbookParameterMappings AS RPM ON R.ServiceId = RPM.ServiceId INNER JOIN dbo.RequestParameters AS RP ON RPM.ParameterName = RP.[Key] AND R.RequestId = RP.RequestId where RP.RequestId = '$RequestID' order by [Order]" $html = "<table><tr><td><b>Question</b></td><td><b>Answer</b></td></tr>" $html = "<table>" foreach ($row in $Result) { $row $html += "<tr><td><b>" + $row.Question + "</b></td><td>" + $row.Value + "</td></tr>" } $html += "</table>" $f_RequestInfo = ExecuteSqlQuery -sqlquery "select InitiatedBy, TargetUserId,[ApprovedBy], [ApprovedTime], Comment from Requests where RequestId = '$RequestID'" $Connection.Close() Remove-Variable -Scope Global -Name Connection $f_SamInitiatedBy = $f_RequestInfo.InitiatedBy.Split("\")[1] $f_UserInitiatedBy = Get-ADUser -Identity $f_SamInitiatedBy -Properties Mail $f_SamTarget = $f_RequestInfo.TargetUserId.Split("\")[1] $f_UserTarget = Get-ADUser -Identity $f_SamTarget -Properties Mail $return.InitiatedBy = $f_RequestInfo.InitiatedBy $return.MailInitiatedBy = $f_UserInitiatedBy.mail $return.MailTarget = $f_UserTarget.mail $return.TargetUserId = $f_RequestInfo.TargetUserId $return.ApprovedBy = $f_RequestInfo.ApprovedBy $return.ApprovedTime = $f_RequestInfo.ApprovedTime $return.Comment = $f_RequestInfo.Comment $return.HTML = $HTML return $return } Function Get-MailContent ($RequestID, $RequestTitle, $EndDate, $TargetUserId, $InitiatedBy, $Status, $PortalURL, $RequestedBy, $AdditionalHTML, $InputHTML) { $f_RequestID = $RequestID $f_InitiatedBy = $InitiatedBy $f_RequestTitle = $RequestTitle $f_EndDate = $EndDate $f_RequestStatus = $Status $f_RequestLink = "$PortalURL/requeststatus?id=$RequestID" $f_RequestedBy = $RequestedBy $f_HTMLINFO = $AdditionalHTML $f_InputHTML = $InputHTML $f_SamInitiatedBy = $f_InitiatedBy.Split("\")[1] $f_UserInitiatedBy = Get-ADUser -Identity $f_SamInitiatedBy -Properties DisplayName $f_DisplaynameInitiatedBy = $f_UserInitiatedBy.DisplayName $HTML = @' <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 1.5pt; background: #F7F8F3; mso-yfti-tbllook: 1184;" border="0" width="100%" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes;"> <td style="padding: .75pt .75pt .75pt .75pt;" valign="top"> </td> <td style="width: 450.0pt; padding: .75pt .75pt .75pt .75pt; box-sizing: border-box;" valign="top" width="600"> <div style="box-sizing: border-box;"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; background: white; border: solid #E9E9E9 1.0pt; mso-border-alt: solid #E9E9E9 .75pt; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm;" border="1" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes;"> <td style="border: none; background: #6ddc36; padding: 15.0pt 0cm 15.0pt 15.0pt;" valign="top"> <p class="MsoNormal" style="line-height: 19.2pt;"><img src="https://au2mator.com/wp-content/uploads/2018/02/HPLogoau2mator-1.png" alt="" width="198" height="43" /></p> </td> </tr> <tr style="mso-yfti-irow: 1; box-sizing: border-box;"> <td style="border: none; padding: 15.0pt 15.0pt 15.0pt 15.0pt; box-sizing: border-box;" valign="top"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm; box-sizing: border-box;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes; box-sizing: border-box;"> <td style="padding: 0cm 0cm 15.0pt 0cm; box-sizing: border-box;" valign="top"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm; box-sizing: border-box;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes; box-sizing: border-box;"> <td style="width: 55.0%; padding: 0cm 0cm 0cm 0cm; box-sizing: border-box;" valign="top" width="55%"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes;"> <td style="width: 18.75pt; border-top: solid #E3E3E3 1.0pt; border-left: solid #E3E3E3 1.0pt; border-bottom: none; border-right: none; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-left-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 0cm 0cm; box-sizing: border-box;" width="25"> <p class="MsoNormal" style="text-align: center; line-height: 19.2pt;" align="center"> </p> </td> <td style="border-top: solid #E3E3E3 1.0pt; border-left: none; border-bottom: none; border-right: solid #E3E3E3 1.0pt; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-right-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 3.75pt 0cm; font-color: #0000;"><strong>End Date</strong>: ##EndDate</td> </tr> <tr style="mso-yfti-irow: 1;"> <td style="border-top: solid #E3E3E3 1.0pt; border-left: solid #E3E3E3 1.0pt; border-bottom: none; border-right: none; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-left-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 0cm 0cm;"> <p class="MsoNormal" style="text-align: center; line-height: 19.2pt;" align="center"> </p> </td> <td style="border-top: solid #E3E3E3 1.0pt; border-left: none; border-bottom: none; border-right: solid #E3E3E3 1.0pt; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-right-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 3.75pt 0cm;"><strong>Status</strong>: ##Status</td> </tr> <tr style="mso-yfti-irow: 2; mso-yfti-lastrow: yes;"> <td style="border: solid #E3E3E3 1.0pt; border-right: none; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-left-alt: solid #E3E3E3 .75pt; mso-border-bottom-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 3.75pt 0cm;"> <p class="MsoNormal" style="text-align: center; line-height: 19.2pt;" align="center"> </p> </td> <td style="border: solid #E3E3E3 1.0pt; border-left: none; mso-border-top-alt: solid #E3E3E3 .75pt; mso-border-bottom-alt: solid #E3E3E3 .75pt; mso-border-right-alt: solid #E3E3E3 .75pt; padding: 0cm 0cm 3.75pt 0cm;"><strong>Requested By</strong>: ##RequestedBy</td> </tr> </tbody> </table> </td> <td style="width: 5.0%; padding: 0cm 0cm 0cm 0cm; box-sizing: border-box;" width="5%"> <p class="MsoNormal" style="line-height: 19.2pt;"><span style="font-size: 9.0pt; font-family: 'Helvetica',sans-serif; mso-fareast-font-family: 'Times New Roman';"> </span></p> </td> <td style="width: 40.0%; padding: 0cm 0cm 0cm 0cm; box-sizing: border-box;" valign="top" width="40%"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; background: #FAFAFA; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes;"> <td style="width: 100.0%; border: solid #E3E3E3 1.0pt; mso-border-alt: solid #E3E3E3 .75pt; padding: 7.5pt 0cm 1.5pt 3.75pt;" width="100%"> <p style="text-align: center;" align="center"><span style="font-size: 10.5pt; color: #959595;">Request ID</span></p> <p class="MsoNormal" style="text-align: center;" align="center"> </p> <p style="text-align: center;" align="center"><u><span style="font-size: 12.0pt; color: black;"><a href="##RequestLink"><span style="color: black;">##REQUESTID</span></a></span></u></p> <p class="MsoNormal" style="text-align: center;" align="center"><span style="mso-fareast-font-family: 'Times New Roman';"> </span></p> </td> </tr> </tbody> </table> </td> </tr> </tbody> </table> </td> </tr> </tbody> </table> </td> </tr> <tr style="mso-yfti-irow: 2; box-sizing: border-box;"> <td style="border: none; padding: 0cm 15.0pt 15.0pt 15.0pt; box-sizing: border-box;" valign="top"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm; box-sizing: border-box;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; box-sizing: border-box;"> <td style="padding: 0cm 0cm 15.0pt 0cm; box-sizing: border-box;" valign="top"> <p class="MsoNormal" style="line-height: 19.2pt;"><strong><span style="font-size: 10.5pt; font-family: 'Helvetica',sans-serif; mso-fareast-font-family: 'Times New Roman';">Dear ##UserDisplayname,</span></strong></p> </td> </tr> <tr style="mso-yfti-irow: 1; box-sizing: border-box;"> <td style="padding: 0cm 0cm 15.0pt 0cm; box-sizing: border-box;" valign="top"> <p class="MsoNormal" style="line-height: 19.2pt;"><span style="font-size: 10.5pt; font-family: 'Helvetica',sans-serif; mso-fareast-font-family: 'Times New Roman';">the Request <strong>"##RequestTitle"</strong> has been finished.<br /> <br /> Please see the description for detailed information.<br /><b>##HTMLINFO </b><br /></span></p> <div> </div> <div>See the Details of the Request</div> <div>##InputHTML</div> <div> </div> <div> </div> Kind regards,<br /> au2mator Self Service Team <p> </p> </td> </tr> <tr style="mso-yfti-irow: 2; mso-yfti-lastrow: yes; box-sizing: border-box;"> <td style="padding: 0cm 0cm 15.0pt 0cm; box-sizing: border-box;" valign="top"> <p class="MsoNormal" style="text-align: center; line-height: 19.2pt;" align="center"><span style="font-size: 10.5pt; font-family: 'Helvetica',sans-serif; mso-fareast-font-family: 'Times New Roman';"><a style="border-radius: 3px; -webkit-border-radius: 3px; -moz-border-radius: 3px; display: inline-block;" href="##RequestLink"><strong><span style="color: white; border: solid #50D691 6.0pt; padding: 0cm; background: #50D691; text-decoration: none; text-underline: none;">View your Request</span></strong></a></span></p> </td> </tr> </tbody> </table> </td> </tr> <tr style="mso-yfti-irow: 3; mso-yfti-lastrow: yes; box-sizing: border-box;"> <td style="border: none; padding: 0cm 0cm 0cm 0cm; box-sizing: border-box;" valign="top"> <table class="MsoNormalTable" style="width: 100.0%; mso-cellspacing: 0cm; background: #333333; mso-yfti-tbllook: 1184; mso-padding-alt: 0cm 0cm 0cm 0cm;" border="0" width="100%" cellspacing="0" cellpadding="0"> <tbody> <tr style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes; box-sizing: border-box;"> <td style="width: 50.0%; border: none; border-right: solid lightgrey 1.0pt; mso-border-right-alt: solid lightgrey .75pt; padding: 22.5pt 15.0pt 22.5pt 15.0pt; box-sizing: border-box;" valign="top" width="50%"> </td> <td style="width: 50.0%; padding: 22.5pt 15.0pt 22.5pt 15.0pt; box-sizing: border-box;" valign="top" width="50%"> </td> </tr> </tbody> </table> </td> </tr> </tbody> </table> </div> </td> <td style="padding: .75pt .75pt .75pt .75pt; box-sizing: border-box;" valign="top"> </td> </tr> </tbody> </table> <p class="MsoNormal"><span style="mso-fareast-font-family: 'Times New Roman';"> </span></p> '@ $html = $html.replace('##REQUESTID', $f_RequestID).replace('##UserDisplayname', $f_DisplaynameInitiatedBy).replace('##RequestTitle', $f_RequestTitle).replace('##EndDate', $f_EndDate).replace('##Status', $f_RequestStatus).replace('##RequestedBy', $f_RequestedBy).replace('##HTMLINFO', $f_HTMLINFO).replace('##InputHTML', $f_InputHTML).replace('##RequestLink', $f_RequestLink) return $html } function Send-ServiceMail ($HTMLBody, $ServiceName, $Recipient, $RequestID, $RequestStatus) { $f_Subject = "au2mator - $ServiceName Request [$RequestID] - $RequestStatus" if ($SMPTAuthentication) { #$f_secpasswd = ConvertTo-SecureString $SMTPPassword -AsPlainText -Force $f_mycreds = New-Object System.Management.Automation.PSCredential ($SMTPUser, $SMTPPassword) if ($EnableSSLforSMTP) { Send-MailMessage -SmtpServer $SMTPServer -To $Recipient -From $SMTPSender -Subject $f_Subject -Body $HTMLBody -BodyAsHtml -Priority high -Credential $f_mycreds -UseSsl } else { Send-MailMessage -SmtpServer $SMTPServer -To $Recipient -From $SMTPSender -Subject $f_Subject -Body $HTMLBody -BodyAsHtml -Priority high -Credential $f_mycreds } } else { if ($EnableSSLforSMTP) { Send-MailMessage -SmtpServer $SMTPServer -To $Recipient -From $SMTPSender -Subject $f_Subject -Body $HTMLBody -BodyAsHtml -Priority high -UseSsl } else { Send-MailMessage -SmtpServer $SMTPServer -To $Recipient -From $SMTPSender -Subject $f_Subject -Body $HTMLBody -BodyAsHtml -Priority high } } } #endregion Functions #region Script Write-au2matorLog -Type INFO -Text "Start Script" if ($DoImportPSSession) { Write-au2matorLog -Type INFO -Text "Import-Pssession" $PSSession = New-PSSession -ComputerName $DCServer Import-PSSession -Session $PSSession -DisableNameChecking -AllowClobber } else { } Write-au2matorLog -Type INFO -Text "Import AD PS Module" Import-Module ActiveDirectory Write-au2matorLog -Type INFO -Text "Try to add User in Group" if (Get-ADGroupMember -Identity $c_Group | Where-Object -Property DistinguishedName -Value $c_User -EQ) { Write-au2matorLog -Type INFO -Text "User is already in Group" $au2matorReturn = "User $c_User is already in Group $c_Group" $AdditionalHTML="<br> User " + (Get-ADUser -identity $c_User).DisplayName +" was already a Member of the Group "+(Get-ADGroup -Identity $c_Group).DisplayName+" <br> " $Status = "COMPLETED" } else { try { Add-ADGroupMember -Identity $c_Group -Members $c_User Write-au2matorLog -Type INFO -Text "User added in Group" } catch { $ErrorCount = 1 Write-au2matorLog -Type ERROR -Text "Error on adding User in Group" Write-au2matorLog -Type ERROR -Text $Error } if ($ErrorCount -eq 0) { $au2matorReturn = "User $c_User added in Group $c_Group" $AdditionalHTML="<br> User " + (Get-ADUser -identity $c_User).DisplayName +" added in Group "+(Get-ADGroup -Identity $c_Group).DisplayName+" <br> " $Status = "COMPLETED" } else { $au2matorReturn = "failed to add $c_User in Group $c_Group, Error: $Error" $Status = "ERROR" } } #endregion Script #region Return ## return to au2mator Services Write-au2matorLog -Type INFO -Text "Service finished" if ($SendMailToInitiatedByUser) { Write-au2matorLog -Type INFO -Text "Send Mail to Initiated By User" $UserInput = Get-UserInput -RequestID $RequestId $HTML = Get-MailContent -RequestID $RequestId -RequestTitle $Service -EndDate $UserInput.ApprovedTime -TargetUserId $TargetUserId -InitiatedBy $InitiatedBy -Status $Status -PortalURL $PortalURL -RequestedBy $InitiatedBy -AdditionalHTML $AdditionalHTML -InputHTML $UserInput.html Send-ServiceMail -HTMLBody $HTML -RequestID $RequestId -Recipient "$($UserInput.MailInitiatedBy)" -RequestStatus $Status -ServiceName $Service } if ($SendMailToTargetUser) { Write-au2matorLog -Type INFO -Text "Send Mail to Target User" $UserInput = Get-UserInput -RequestID $RequestId $HTML = Get-MailContent -RequestID $RequestId -RequestTitle $Service -EndDate $UserInput.ApprovedTime -TargetUserId $TargetUserId -InitiatedBy $InitiatedBy -Status $Status -PortalURL $PortalURL -RequestedBy $InitiatedBy -AdditionalHTML $AdditionalHTML -InputHTML $UserInput.html Send-ServiceMail -HTMLBody $HTML -RequestID $RequestId -Recipient "$($UserInput.MailTarget)" -RequestStatus $Status -ServiceName $Service } return $au2matorReturn #endregion Return |