Vous pouvez écrire un script PowerShell qui est exécuté par un service planifié sur un contrôleur de domaine qui localise tous les utilisateurs dont les mots de passe expirent dans un certain temps et e-mails chaque utilisateur une notification. Les exigences de cette solution comprennent une version assez récente de PowerShell (2.0 ou plus pourrait suffire), un serveur relais SMTP d'un certain point, et des champs d'adresse e-mail remplis dans AD pour chaque utilisateur. Le script doit être exécuté avec des privilèges élevés.
$from = "<administrator@example.com>"
$subject = "Your password on the domain example.com is expiring soon"
$smtpServer = "smtprelay.example.com"
$today = Get-Date
# An HTML formatted e-mail body has been created and saved to a text file.
# This command reads the file into an array, each array element is one line of the file.
$bodyArray = Get-Content -Path "C:\ScriptData\emailbody.txt"
# The e-mail command won't correctly send the array for the e-mail body, we have to convert it to a stream of text.
for ($i=0; $i -lt $bodyArray.Count; $i++) {
$body += $bodyArray[$i]
}
# Regarding the dates in this next command, it's meant to get passwords
# expiring within seven days (that's where the 8 comes from) and exclude
# passwords that have already expired. In AD, numerical zero means 1/1/1600,
# but outside of AD numerical zero is 1/1/1, so 1600 years must be added to
# dates retrieved from AD to compare them to dates computed in PowerShell
# using Get-Date.
$expiringUsers = Get-ADUser -Filter {Enabled -eq $True -and PasswordNeverExpires -eq $False} -Properties "GivenName","samAccountName","EmailAddress","msDS-UserPasswordExpiryTimeComputed" | Where-Object {((Get-Date($_.'msDS-UserPasswordExpiryTimeComputed')).AddYears(1600) -lt (Get-Date).AddDays(8)) -and ((Get-Date($_.'msDS-UserPasswordExpiryTimeComputed')).AddYears(1600) -gt (Get-Date))}
foreach ($user in $expiringUsers) {
$timeRemaining = New-TimeSpan -Start $today -End (Get-Date($user.'msDS-UserPasswordExpiryTimeComputed')).AddYears(1600)
$daystopassexpiry = $timeRemaining.Days
# The next command replaces what I'll call constants in the e-mail body file
# with the values retrieved from the user's AD information. This
# personalizes each e-mail.
$newbody = $body -replace "--GIVENNAME--",$user.GivenName -replace "--USERNAME--",$user.SamAccountName -replace "--NUMBER OF DAYS--",$daystopassexpiry -replace "--EMAILADDRESS--",$user.EmailAddress
Send-MailMessage -From $from -To $user.EmailAddress -Subject $subject -BodyAsHTML -Body $newbody -SmtpServer $smtpServer
$newbody = $null
}
Je suggère d'ajouter la détection des erreurs ( try/catch
) et si vous l'exécutez en tant que tâche planifiée, j'aime ajouter une fonction d'enregistrement en utilisant la commande Start-Transcript
pour que je puisse plus facilement comprendre ce qui a mal tourné. Je suggère également d'ajouter un -BCC
à la Send-MailMessage
cmdlet à vous-même afin que vous puissiez vous assurer que les courriels arrivent et sont formatés correctement.
J'ai créé le corps de l'e-mail en créant un e-mail qui ressemblait à ce que je voulais, avec toutes les "constantes" écrites, puis je me le suis envoyé, et ensuite j'ai visualisé la source de l'e-mail et l'ai copiée dans un fichier texte.