@@ -14,6 +14,7 @@ import-module Az.Accounts -Force
1414import-module Az.KeyVault - Force
1515import-module PnP.PowerShell - Force
1616import-module ImportExcel - Force
17+ import-module Az.Storage - Force
1718
1819# Write an information log with the current time.
1920Write-Host " v1.6 PowerShell timer trigger function ran! TIME: $currentUTCtime "
@@ -69,23 +70,125 @@ function Send-Email {
6970 Send-MailMessage - From $from - To $to - Subject $subject - Body $body - SmtpServer $smtpServer - Port $smtpPort - Credential $credential - UseSsl
7071}
7172
73+ function Test-CertificateExpiry {
74+ param (
75+ [Parameter (Mandatory = $true )]
76+ [string ]$Thumbprint ,
77+
78+ [Parameter (Mandatory = $true )]
79+ [System.Security.SecureString ]$SmtpPassword ,
80+
81+ [Parameter (Mandatory = $false )]
82+ [int ]$WarningDays = 30
83+ )
84+
85+ try {
86+ # Get certificate from the store
87+ $cert = Get-ChildItem - Path " Cert:\LocalMachine\My\$Thumbprint " - ErrorAction Stop
88+ if (-not $cert ) {
89+ throw " Certificate with thumbprint $Thumbprint not found"
90+ }
91+
92+ # Calculate days until expiry
93+ $daysUntilExpiry = ($cert.NotAfter - (Get-Date )).Days
94+
95+ # Create email body with certificate details
96+ $emailBody = @"
97+ Certificate Details:
98+ -------------------
99+ Subject: $ ( $cert.Subject )
100+ Thumbprint: $ ( $cert.Thumbprint )
101+ Expiry Date: $ ( $cert.NotAfter )
102+ Days Remaining: $daysUntilExpiry
103+
104+ Please ensure the certificate is renewed before expiration.
105+ "@
106+
107+ # Check if warning needed and not already sent today
108+ if ($daysUntilExpiry -le $WarningDays ) {
109+ # Connect to Azure Storage
110+ $storageAccount = Get-AzStorageAccount - ResourceGroupName " htupdatechecker" - Name " htupdatechecker"
111+ $ctx = $storageAccount.Context
112+
113+ # Create table if it doesn't exist
114+ $tableName = " CertificateWarnings"
115+ $table = Get-AzStorageTable - Name $tableName - Context $ctx - ErrorAction SilentlyContinue
116+ if (-not $table ) {
117+ $table = New-AzStorageTable - Name $tableName - Context $ctx
118+ }
119+
120+ # Check last warning date
121+ $lastWarning = Get-AzTableRow - Table $table.CloudTable - PartitionKey " Certificates" - RowKey $Thumbprint - ErrorAction SilentlyContinue
122+ $today = (Get-Date ).Date
123+
124+ if (-not $lastWarning -or ([DateTime ]$lastWarning.LastWarningDate ).Date -lt $today ) {
125+ # Send warning email
126+ Send-Email `
127+ - subject " Certificate Expiry Warning - $ ( $cert.Subject ) " `
128+ - version " " `
129+ - securePassword $SmtpPassword `
130+ - body $emailBody
131+
132+ # Update or add warning record
133+ if ($lastWarning ) {
134+ $lastWarning.LastWarningDate = $today
135+ $lastWarning | Update-AzTableRow - Table $table.CloudTable
136+ } else {
137+ Add-AzTableRow `
138+ - Table $table.CloudTable `
139+ - PartitionKey " Certificates" `
140+ - RowKey $Thumbprint `
141+ - Property @ {
142+ " LastWarningDate" = $today
143+ " CertificateSubject" = $cert.Subject
144+ }
145+ }
146+
147+ Write-Warning " Certificate will expire in $daysUntilExpiry days - Warning email sent"
148+ } else {
149+ Write-Information " Certificate expiry warning already sent today"
150+ }
151+ return $false
152+ }
153+
154+ Write-Information " Certificate valid for $daysUntilExpiry days"
155+ return $true
156+ }
157+ catch {
158+ $errorMessage = " Error checking certificate expiry: $_ "
159+ Write-Error $errorMessage
160+
161+ # Send error notification (errors always send regardless of daily limit)
162+ Send-Email `
163+ - subject " Certificate Check Error" `
164+ - version " " `
165+ - securePassword $SmtpPassword `
166+ - body $errorMessage
167+
168+ return $false
169+ }
170+ }
171+
72172# Main function to be triggered by the Azure Function
73173function RunFunction {
74174 param ($Timer )
75175
76- # try {
176+ try {
77177 Connect-AzAccount - Identity
78178
79179 # Retrieve secrets from Azure Key Vault
80180 $vaultName = " huntertechvault"
81181 $tenantid = Get-AzKeyVaultSecret - VaultName $vaultName - Name " tenantid" - AsPlainText
82182 $appid = Get-AzKeyVaultSecret - VaultName $vaultName - Name " appid" - AsPlainText
83183 $thumbprint = " F87409186E7544C2D93B79931987BF2BE313E336"
84-
85- # $certsecret = Get-AzKeyVaultSecret -VaultName $vaultName -Name "fl-mailbox" -AsPlainText
86-
87184 $smtp2go = ConvertTo-SecureString (Get-AzKeyVaultSecret - VaultName $vaultName - Name " smtp2go-secure" - AsPlainText) - AsPlainText - Force
88185
186+ # Check certificate expiry
187+ $certValid = Test-CertificateExpiry - Thumbprint $thumbprint - SmtpPassword $smtp2go
188+ if (-not $certValid ) {
189+ Write-Warning " Certificate expiry check failed or certificate needs renewal"
190+ }
191+
89192 # Connect to SharePoint and get project list
90193 connect-pnponline - Url " https://firstlightca.sharepoint.com/sites/firstlightfiles" - Tenant $tenantid - ApplicationId $appid - Thumbprint $thumbprint
91194 $web = Get-PnPWeb
@@ -152,17 +255,17 @@ function RunFunction {
152255 remove-item - path " D:\local\projects.xlsx" - force
153256 disconnect-pnponline
154257 disconnect-azaccount
155- # }
156- # catch {
157- # Write-Error "Error in main function: $_"
158- # Send-Email -subject "Project Processing Error" `
159- # -version "" `
160- # -securePassword $smtp2go `
161- # -body "Function failed with error: $_"
162- # }
163- # finally {
164- # Clear-TempFiles
165- # }
258+ }
259+ catch {
260+ Write-Error " Error in main function: $_ "
261+ Send-Email - subject " Project Processing Error" `
262+ - version " " `
263+ - securePassword $smtp2go `
264+ - body " Function failed with error: $_ "
265+ }
266+ finally {
267+ Clear-TempFiles
268+ }
166269}
167270
168271# Timer trigger to run the function periodically
0 commit comments