Graph API: Follow SharePoint Online Sites


[SharePoint Online] has several social media-esque features baked into the solution. One such feature, choosing to “follow” specific SPO sites. But this is a manual action performed by each individual. That is, unless the Microsoft Graph API is used to follow a site on a person’s behalf…

Figure 1 – SharePoint Online sites being followed.

Example Scenario:

New hires should have the Company Intranet readily accessible on their first day. The simplest solution would likely be creating a shortcut on their desktop. Or bookmarking the site in their default browser. Or maybe even setting the intranet as the browser home page. But what if they switch browsers or switch devices?

To alleviate this, SharePoint Online is accessible from any device and any browser, and persists user settings. Additionally, SPO has a dedicated mobile app. Because of this, followed sites are easy to find nonetheless. And with this in mind, an automated solution could be scripted using PowerShell and scheduled as an Azure Runbook. Getting started, the Graph API will need to query the intranet site ID:

  • PowerShell snippet to GET site ID.
function Get-SPOSiteGuid {
    param(
        [Parameter(Mandatory)] [System.String] $RelativePath
    )

    [System.String] $thisGuid = ""
    [System.String] $thisReqs = "/sites/contoso.sharepoint.com:$($RelativePath)"
 
 
    try {
        (Get-APIResponse -APIGetRequest "$thisReqs") | % {
            $thisGuid = "$($_.id)"
        }
    }
    catch [Exception] {}
    return $thisGuid
}


[System.String] $sPath = "/sites/Intranet"
[System.String] $sGuid = (Get-SPOSiteGuid -RelativePath $sPath)

Worth noting, this script should only process new hires. Either filter user objects by Creation time, or use a dedicated security group for new hires. If the latter, then GET the group ID:

  • PowerShell snippet to GET security group ID.
function Get-ADGroupId {
    param(
        [Parameter(Mandatory)] [System.String] $GroupName
    )


    [System.String] $thisGuid = ""
    [System.String] $thisReqs = "/groups?`$select=id,displayName&`$filter=startswith(displayName, '$GroupName')"
 
 
    try {
        (Get-APIResponse -APIGetRequest "$thisReqs").value | % {
            $thisGuid = "$($_.id)"
        }
    }
    catch [Exception] {}
    return $thisGuid
}


[System.String] $gName = "New Hires"
[System.String] $gGuid = (Get-ADGroupId -GroupName $gName)

Using the security group ID, GET and enumerate the group members. For each member, the script will need their user ID:

  • PowerShell snippet to GET security group member IDs.
function Get-ADGroupMembers {
    param(
        [Parameter(Mandatory)] [System.String] $GroupGUID
    )


    [System.Collections.Hashtable] $listOf = @{}
    [System.String] $thisReqs = "/groups/$($GroupGUID)/members?`$select=id,displayName"
 
 
    try {
        (Get-APIResponse -APIGetRequest "$thisReqs").value | % {
            $listOf.Add(
                "$($_.displayName)", "$($_.id)"
            )
        }
    }
    catch [Exception] {}
    return $listOf
}

Finalizing the script, build a batch request object using the user and site IDs, then submit the batch to Microsoft:

  • PowerShell snippet to batch update user site follow list.
[System.Array] $batchOf = @()
foreach($member in ((Get-ADGroupMembers -GroupGUID $gGuid).GetEnumerator())) {


    $batchOf += @{
        "url" = "/users/$($member.Value)/followedSites/add"
        "method" = "POST"
        "id" = "$($batchOf.Count + 1)"
        "body" = @{
            "value" = @(
                @{
                    "id" = "$($sGuid)"
                }
            )
        }
        "headers" = @{
            "Content-Type" = "application/json"
        }
    }
}


if ($batchOf.Length -ne 0) {
    Get-APIBatchResponse -BatchRequests $batchOf
}

Conclusion:
Automation, even for simple tasks, are wins as Azure Runbooks. All scripts don’t have to be complicated…

“Listen how they say your name. If they can’t say that right, there’s no way they’re going to know how to treat you proper, neither.”

Rita Frances Dove

#BlackLivesMatter

Leave a comment