Skip to main content

I was wondering if there is a way to use PowerShell to determine if a machine in a protection group has not backed up in the last 30 days. Obviously in Inventory there are protection groups that have machines in them and a status of “Last Agent Backup”. Is it possible to generate a report that displays that information? 

Basically I would like to put the script into task scheduler and have it run the 2nd and the 24th of every month. 

Any advice?
 

# Load Veeam PowerShell Module
Import-Module Veeam.Backup.PowerShell

# Define protection group names
$protectionGroupNames = @("Example Protection Group", "Example Protection Group 2")

# Get the current date and time window
$timeWindow = (Get-Date).AddDays(-30)

# Initialize array to store report data
$reportData = @()

foreach ($groupName in $protectionGroupNames) {
# Get the protection group
$protectionGroup = Get-VBRProtectionGroup -Name $groupName

# Get details of the machines in the protection group
$machines = Get-VBRDiscoveredComputer -ProtectionGroup $protectionGroup

foreach ($machine in $machines) {
# Get the last backup session for the machine
$lastSession = Get-VBRBackupSession | Where-Object { $_.Name -like "*$($machine.Name)*" } | Sort-Object EndTime -Descending | Select-Object -First 1

# Add to report
$reportData += aPSCustomObject]@{
ProtectionGroup = $groupName
MachineName = $machine.Name
LastBackup = $lastSession.EndTime
Status = $lastSession.State
}
}
}

# Export report to CSV
$reportPath = "C:\Reports\PhysicalInfrastructureBackupReport_$(Get-Date -Format 'yyyyMMdd_HHmmss').csv"
$reportData | Export-Csv -Path $reportPath -NoTypeInformation

 

Not sure if @SteveHeart can assist here?


Could you not use the Windows scheduler for this script on the Veeam server?


Could you not use the Windows scheduler for this script on the Veeam server?

That is what I plan on doing once the script can produce the output I am looking for. Not entirely sure how to get the missing data I am looking for.


So, you’re not getting the desired output from your script? What is it not doing specifically?


Could you not use the Windows scheduler for this script on the Veeam server?

That is what I plan on doing once the script can produce the output I am looking for. Not entirely sure how to get the missing data I am looking for.

Ok well hopefully the gurus here can help with the script.


So, you’re not getting the desired output from your script? What is it not doing specifically?

Correct. I would like the script to tell me which machines in the protection group have not backed up in the last 30 days. 

Under Inventory > Physical Infrastructure > Protection Group there is a column that shows “Last Agent Backup”
 

 


Hi @Cjr20172 - sorry for the confusion I think on my part. So what I’m asking is, does your script work as is, but you’re just wanting to add that additional info about the last backup time? Or, does your script not work at all? Let’s start there… 😊


Hi @Cjr20172 - sorry for the confusion I think on my part. So what I’m asking is, does your script work as is, but you’re just wanting to add that additional info about the last backup time? Or, does your script not work at all? Let’s start there… 😊

Great question! As of right now it works.  It populates the ProtectionGroup column and the MachineName column of the report! What is not working is the Last Backup Agent information. I am not quite sure why it will not pull that information.

 

 


@Cjr20172 - ok, great.

So, when I write PS scripts with Sort, I generally have issues with it and when I have it in my script I tend not to get data in my output. Just to test, remove the Sort just to see if data is at least retrieved for your LastSession variable and thus Column.


Okay, I removed the Sort and the output of the new file is still the same unfortunately.
 

 


@Cjr20172 - ok, great.

So, when I write PS scripts with Sort, I generally have issues with it and when I have it in my script I tend not to get data in my output. Just to test, remove the Sort just to see if data is at least retrieved for your LastSession variable and thus Column.

Forgot to reply this way. 

 

 Okay, I removed the Sort and the output of the new file is still the same unfortunately.
 

 


@Cjr20172 - ok, great.

So, when I write PS scripts with Sort, I generally have issues with it and when I have it in my script I tend not to get data in my output. Just to test, remove the Sort just to see if data is at least retrieved for your LastSession variable and thus Column.

Forgot to reply this way. 

 

 Okay, I removed the Sort and the output of the new file is still the same unfortunately.
 

 

Then it might be a different variable that you need to use in the script.

 
 
 

Ok @Cjr20172 ...go ahead and add it back in. Did you look at the Veeam PoSH reference for that cmdlet? It looks like you have the correct syntax...um...almost:

https://helpcenter.veeam.com/docs/backup/powershell/get-vbrbackupsession.html?ver=120

So, for your sort object, it looks like the EndTime option should actually be EndTimeUTC. Wanna try that to see if any data is then retrieved? Expand Example 3 for details.


Ok @Cjr20172 ...go ahead and add it back in. Did you look at the Veeam PoSH reference for that cmdlet? It looks like you have the correct syntax...um...almost:

https://helpcenter.veeam.com/docs/backup/powershell/get-vbrbackupsession.html?ver=120

So, for your sort object, it looks like the EndTime option should actually be EndTimeUTC. Wanna try that to see if any data is then retrieved? Expand Example 3 for details.

I have not referenced that. Thank you for the link! I will take a look at that and update the script accordingly.


No problem. Let me know if that helps.


You should ask the question in the veeam forum, they have a section dedicated to PowerShell. 

https://forums.veeam.com/powershell-f26/


@Cjr20172 & @coolsport00,

I’ll have a look into it on my “Scripting Friday”. Interesting, the script seems to read out values. For a protection group I get a value for one host, but no value for the other host. I think the error resides here:

Where-Object { $_.Name -like "*$($machine.Name)*" }
 


Stay tuned.
Cheers,
Steve


@Cjr20172,
you need to use the Agent related commands. Some inspiration can be found here.

Cheers,
Steve


Ah, ok. Great!..thanks for the assist Steve. I don’t have any protection groups set up, so couldn’t really test anything out.


@Cjr20172,
you need to use the Agent related commands. Some inspiration can be found here.

Cheers,
Steve

Thanks for the assistance Steve. Didn't realize you needed some agent pieces. 😎


Hey everyone, 

Thank you all for the help and insight.
I wanted to let everyone know I decided to go about the task a different way.

Instead of going through agents in the protection group, I have gone through the restore points under Backups > Disk. 

This script imports the Veeam Backup PowerShell module, defines a date threshold 30 days prior to the current date to determine recent backups, allows user specification of Veeam backup job names to be included in the report, fetches all restore points from the specified Veeam backup jobs, filters the restore points to include only the most recent restore point for each machine within the specified jobs, Groups the restore points by machine name and selects the most recent one based on creation time.

Here is the script (tested and working) if anyone wants to use it or might find it helpful
 

# Load Veeam PowerShell Module
Import-Module Veeam.Backup.PowerShell

# Define the date threshold (last 30 days)
$thresholdDate = (Get-Date).AddDays(-30)

# Specify the job names to check (replace with your actual job names)
$jobNamesToCheck = @("JobName1", "JobName2")

# Initialize array to store report data
$reportData = @()

# Get all machines (VMs or physical) that have restore points from specified jobs
$restorePoints = Get-VBRRestorePoint | Where-Object { $jobNamesToCheck -contains $_.JobName } | Group-Object -Property Name | ForEach-Object {
$_.Group | Sort-Object CreationTime -Descending | Select-Object -First 1
}

foreach ($restorePoint in $restorePoints) {
$machineName = $restorePoint.Name
$creationTime = $restorePoint.CreationTime

# Determine backup status
$backedUp = if ($creationTime -gt $thresholdDate) { "Yes" } else { "No" }

# Add machine to report data
$reportData += tPSCustomObject]@{
MachineName = $machineName
BackedUp = $backedUp
LastBackupDate = $creationTime
}
}

# Sort report data by BackedUp status and then by MachineName alphabetically
$reportData = $reportData | Sort-Object BackedUp, MachineName

# Export report to CSV
$reportPath = "C:\Reports\BackupStatusReport_$(Get-Date -Format 'yyyyMMdd_HHmmss').csv"
$reportData | Export-Csv -Path $reportPath -NoTypeInformation

# Display grouped report data
$reportData | Format-Table -GroupBy BackedUp -Property MachineName, LastBackupDate -AutoSize

# Optionally, output to console for review
$reportData

 


Glad to hear you got it sorted @Cjr20172 


Thanks for sharing @Cjr20172 and glad to see you found a workaround.


Comment