janikvonrotz
1/2/2014 - 1:05 PM

PowerShell: Update SharePoint User Alerts #PowerShell #SharePoint

PowerShell: Update SharePoint User Alerts #PowerShell #SharePoint

<?xml version="1.0" encoding="UTF-16"?>
<Task version="1.2" xmlns="http://schemas.microsoft.com/windows/2004/02/mit/task">
  <RegistrationInfo>
    <Date>2013-03-20T14:18:21.6393172</Date>
    <Author>Janik von Rotz (http://janikvonrotz.ch)</Author>
	<Description>Update SharePoint User Alerts</Description>
  </RegistrationInfo>
  <Triggers>
    <CalendarTrigger>
      <StartBoundary>2013-01-01T03:00:00</StartBoundary>
      <Enabled>true</Enabled>
      <ScheduleByDay>
        <DaysInterval>1</DaysInterval>
      </ScheduleByDay>
    </CalendarTrigger>
  </Triggers>
  <Settings>
    <MultipleInstancesPolicy>IgnoreNew</MultipleInstancesPolicy>
    <DisallowStartIfOnBatteries>true</DisallowStartIfOnBatteries>
    <StopIfGoingOnBatteries>true</StopIfGoingOnBatteries>
    <AllowHardTerminate>true</AllowHardTerminate>
    <StartWhenAvailable>false</StartWhenAvailable>
    <RunOnlyIfNetworkAvailable>false</RunOnlyIfNetworkAvailable>
    <IdleSettings>
      <StopOnIdleEnd>true</StopOnIdleEnd>
      <RestartOnIdle>false</RestartOnIdle>
    </IdleSettings>
    <AllowStartOnDemand>true</AllowStartOnDemand>
    <Enabled>true</Enabled>
    <Hidden>false</Hidden>
    <RunOnlyIfIdle>false</RunOnlyIfIdle>
    <WakeToRun>false</WakeToRun>
    <ExecutionTimeLimit>P3D</ExecutionTimeLimit>
    <Priority>7</Priority>
  </Settings>
  <Actions Context="Author">
    <Exec>
      <Command>$PSapps.PowerShell</Command>
      <Arguments>$(Get-ChildItem -Path $PSscripts.Path -Filter "Update-SPUserAlerts.ps1" -Recurse).Fullname</Arguments>
      <WorkingDirectory>$PSProfile.Path</WorkingDirectory>
    </Exec>
  </Actions>
</Task>
<#
$Metadata = @{
	Title = "Update SharePoint User Alerts"
	Filename = "Update-SPUserAlerts.ps1"
	Description = ""
	Tags = "powershell, sharepoint, update, user, alerts"
	Project = ""
	Author = "Janik von Rotz"
	AuthorContact = "http://janikvonrotz.ch"
	CreateDate = "2014-01-02"
	LastEditDate = "2014-01-02"
	Url = ""
	Version = "1.0.0"
	License = @'
This work is licensed under the Creative Commons Attribution-ShareAlike 3.0 Switzerland License.
To view a copy of this license, visit http://creativecommons.org/licenses/by-sa/3.0/ch/ or 
send a letter to Creative Commons, 444 Castro Street, Suite 900, Mountain View, California, 94041, USA.
'@
}
#>

try{

    #--------------------------------------------------#
    # modules
    #--------------------------------------------------#
    if((Get-PSSnapin 'Microsoft.SharePoint.PowerShell' -ErrorAction SilentlyContinue) -eq $null){Add-PSSnapin 'Microsoft.SharePoint.PowerShell'}
    Import-Module ActiveDirectory
    
    #--------------------------------------------------#
    # settings
    #--------------------------------------------------#
    $Alerts = @(    
        @{    
            ID = 1
            ListUrl = "http://sharepoint.domain.ch/site/subsite/Lists/ListName/view.aspx"    
            SubscriberADUsersAndGroups = "ADGroup","ADUser"          
            Title = "`"Benachrichtigunggg `$Username`""
            AlertType = [Microsoft.SharePoint.SPAlertType]::List       
            DeliveryChannels = [Microsoft.SharePoint.SPAlertDeliveryChannels]::Email
            EventType = [Microsoft.SharePoint.SPEventType]::Add
            AlertFrequency = [Microsoft.SharePoint.SPAlertFrequency]::Immediate
            ListViewName = "View 2014"
            FilterIndex = 8
        }
    )
    
    #--------------------------------------------------#
    # function
    #--------------------------------------------------#
    function New-UnifiedAlertObject{
        
        param(
            $Title,
            $AlertType,
            $DeliveryChannels,
            $EventType,
            $AlertFrequency,
            $ListViewID,
            $FilterIndex
        )
        
        New-Object PSObject -Property @{
            Title = $Title
            AlertType = $AlertType
            DeliveryChannels = $DeliveryChannels
            EventType = $EventType
            AlertFrequency = $AlertFrequency
            ListViewID = $ListViewID
            AlertFilterIndex = $AlertFilterIndex
        }
    }

    #--------------------------------------------------#
    # main
    #--------------------------------------------------#
    
    $Alerts | %{
    
        # set vars
        $Message = "Update alerts with ID: $($_.ID)`n"
        $Alert = $_
    
        # get sp site
        $SPWeb = Get-SPWeb (Get-SPUrl $_.ListUrl).WebUrl

        # get name of the list
        $ListName = (Get-SPUrl $_.ListUrl).Url -replace ".*/",""

        # get the sp list object
        $SPList = $SPWeb.Lists[$ListName]
        
        $SPUsers = Get-SPUser -Web $SPWeb.Site.Url
        
        # get the id of the list view by name
        $SPListViewID = ($SPList.Views | where{$_.title -eq $SPListViewName -and $_.title -ne ""} | select -First 1).ID
        
        # get existing alerts
        $ExistingAlerts = $SPWeb.Alerts | where{$_.Properties["alertid"] -eq $Alert.ID}
        
        # cycle throught all users and  update, create or delete their alerts
        $UserWithAlerts = $_.SubscriberADUsersAndGroups | %{
        
            Get-ADObject -Filter {Name -eq $_} | %{
        
                if($_.ObjectClass -eq "user"){
                    
                    Get-ADUser $_.DistinguishedName
                    
                }elseif($_.ObjectClass -eq "group"){
                
                    Get-ADGroupMember $_.DistinguishedName -Recursive | Get-ADUser 
                }
            } | %{
                
                $ADUser = $_
            
                $SPUsers | where{$_.SID -eq $ADUser.SID} | %{$SPWeb.EnsureUser($_.Name)}
            }
        } | %{
        
            # create alert title
            $Username = $_.DisplayName
            $AlertTitle = Invoke-Command -ScriptBlock ([ScriptBlock]::Create($Alert.Title))
            
            # check if already alert exists with this id
            $AlertIS = $_.Alerts | where{$_.Properties["alertid"] -eq $Alert.ID} | select -First 1           
            
            # if exists update this alert
            if($AlertIS){
                
                # create alert objects to compare
                $AlertObjectIS = New-UnifiedAlertObject -Title $AlertIS.title `
                    -AlertType $AlertIS.AlertType `
                    -DeliveryChannels $AlertIS.DeliveryChannels `
                    -EventType $AlertIS.EventType `
                    -AlertFrequency $AlertIS.AlertFrequency `
                    -ListViewID $AlertIS.Properties["filterindex"] `
                    -FilterIndex $AlertIS.Properties["filterindex"]
                    
                $AlertObjectTo = New-UnifiedAlertObject -Title $AlertTitle `
                    -AlertType $Alert.AlertType `
                    -DeliveryChannels $Alert.DeliveryChannels `
                    -EventType $Alert.EventType `
                    -AlertFrequency $Alert.AlertFrequency `
                    -ListViewID $SPListViewID `
                    -FilterIndex $Alert.FilterIndex
                
                # only update changed attributes
                if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property Title, AlertType, DeliveryChannels, EventType, AlertFrequency, ListViewID, FilterIndex){
                    
                    $Message += "Update alert with ID: $($Alert.ID) for user: $($_.DisplayName)`n"
                    
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property Title){$AlertIS.Title = $AlertObjectTo.Title}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property AlertType){$AlertIS.AlertType = $AlertObjectTo.AlertType}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property DeliveryChannels){$AlertIS.DeliveryChannels = $AlertObjectTo.DeliveryChannels}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property EventType){$AlertIS.EventType = $AlertObjectTo.EventType}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property AlertFrequency){$AlertIS.AlertFrequency = $AlertObjectTo.AlertFrequency}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property ListViewID){$AlertIS.Properties["viewid"] = $AlertObjectTo.ListViewID}
                    if(Compare-Object -ReferenceObject $AlertObjectTo -DifferenceObject $AlertObjectIS -Property FilterIndex){$AlertIS.Properties["filterindex"] = $AlertObjectTo.FilterIndex}
                    
                    # update changes
                    $AlertIS.Update()
                }
            }else{
            
                # create a new alert object  
                $Message += "Create alert with ID: $($Alert.ID) for user: $($_.DisplayName)`n"          
                $NewAlert = $_.Alerts.Add()
                
                # add attributes
                $NewAlert.Properties.Add("alertid",$Alert.ID)
                $NewAlert.Title = $AlertTitle                  
                if($SPListViewID){                
                    $NewAlert.Properties.Add("filterindex",$Alert.FilterIndex)
                    $NewAlert.Properties.Add("viewid",$SPListViewID)              
                }
                $NewAlert.AlertType = $Alert.AlertType
                $NewAlert.List = $SPList
                $NewAlert.DeliveryChannels = $Alert.DeliveryChannels
                $NewAlert.EventType = $Alert.EventType
                $NewAlert.AlertFrequency = $Alert.AlertFrequency

                # create the alert
                $NewAlert.Update()
            }
            
            # pipe the users to check alerts to delete
            $_
            
        } 
        
        # username array
        $UserWithAlerts = $UserWithAlerts | %{"$($_.UserLogin)"}
        
        # delete alerts
        $ExistingAlerts | where{$UserWithAlerts -notcontains $_.User} | %{
        
            $Message += "Delete alert with ID: $($Alert.ID) for user: $($_.User)`n"
            $SPWeb.Alerts.Delete($_.ID)        
        }
        
        Write-PPEventLog -Message $Message -Source "Update SharePoint User Alerts" -WriteMessage
    }
}catch{

    Write-PPErrorEventLog -Source "Update SharePoint User Alerts" -ClearErrorVariable    
}