Check If Connected to SPOService in Script

SCENARIO
When executing SharePoint Online scripts you need to be connected to your “admin” site or the script will just fail if you’re not.

PROBLEM
When writing a script you can’t assume that you’re already connected to your SPO tenant and unlike the “msolservice” connect call you need to specify your “admin” URL which can be quite long. But sometimes you’re already connected in the Powershell session.

SOLUTION
Writing this little thing in the start of your script will check if you’re connected to the admin site and if not will call the connect-sposervice command with the URL already set.

# First we reset the sitecheck to avoid having an old result
$sitecheck=""
# This is the address of your SPO admin site
$adminurl = "https://[your tenant name]-admin.sharepoint.com"
# Now we try to get the SPOSITE info for the admin site
Try { $sitecheck = get-sposite $adminurl }
# If we get this server exception for any reason, the service isn't available and we need to take action, in this case
# write it to the console and then connect to the SPO service.
Catch [Microsoft.SharePoint.Client.ServerException]
{
Write-Host -foreground Yellow "You are not connected!"
connect-sposervice $adminurl
}

Manage External Sharing in SharePoint Online

SCENARIO
You’re managing a SharePoint Online environment and you want to know where external sharing is enabled.

PROBLEM
The problem is that Microsoft hasn’t fully launched a way of getting a good overview of this where you can change it. When you first enable sharing for example alot of sites will have it turned on by default etc. The new SharePoint Admin center has the ability to add the “external sharing on/off” column in the list of sites but that is very limited and you can’t enable or disabled it.

SOLUTION
Fortunately there is a very good attribute that you can retrive to get this and alter the external sharing setting called “SharingCapability”.
So using that you can get a list of all sites and what the status is of them, or you can filter for all that have it enabled or disabled:

get-sposite | select url, SharingCapability												# All sites with their URL and SharingCapability
get-sposite | Where-Object{$_.SharingCapability -eq "ExternalUserSharingOnly"}			# External user sharing (share by email) is enabled, but guest link sharing is disabled.
get-sposite | Where-Object{$_.SharingCapability -eq "ExistingExternalUserSharingOnly"}	# External user sharing to existing Azure AD Guest users
get-sposite | Where-Object{$_.SharingCapability -eq "ExternalUserAndGuestSharing"}		# External user sharing (share by email) and guest link sharing are both enabled
get-sposite | Where-Object{$_.SharingCapability -eq "Disabled"} 						# External user sharing disabled

Once you have that you can script it so you can disabled external sharing on all sites by doing this:

$allsites = get-sposite | Where-Object{$_.SharingCapability -ne "Disabled"}
foreach($specificsite in $allsites) { Set-SPOSite $specificsite.url -SharingCapability Disabled }

The reason you want to do this in a “foreach” is there will be a site or two you may get an error that you can’t change the setting, so that would exit the command on that error.

SharePoint 2016 Installation Errors

SCENARIO
You’re trying to install SharePoint 2016 on a Windows 2016 server and thinks just aren’t going well.

PROBLEM
To be honest I don’t know how else to explain the problem in any other way than Microsoft’s Windows Server 2016 team was in a feud over lunchboxes with the SharePoint 2016 devs because there is no other way to describe the complete incompatibility between the two!

SOLUTION
I’d say “Google it!” but that’s probably what got you here in the first place!
The first problem is the prerequisite installer that can’t configure Windows IIS role or download things. Fret not for there is plenty of help to find. When first running the prereq you’ll probably get this error: “Web Server (IIS) Role: configuration error”. To configure the IIS use this Powershell :

Add-WindowsFeature Web-Server,windows-identity-foundation,`NET-Framework-45-ASPNET,Web-Mgmt-Console,Web-Mgmt-Compat,Web-Metabase,Web-Lgcy-Mgmt-Console,Web-Lgcy-Scripting,Web-Mgmt-Tools,Web-WMI,Web-Common-HTTP,NET-HTTP-Activation,NET-Non-HTTP-Activ,NET-WCF-HTTP-Activation45 -Source 'Q:\sources\sxs'

Make sure to edit the source file to the Windows Server 2016 ISO!

The next place you should look at is this blog by the Microsoft Field Engineer Nik. Although be careful about some of his links as those are outdated and replaced with new versions, although downloading the version he’s linking will still work. He even provides a script that will run the Powershell to configure everything. Why this isn’t on the SharePoint 2016 ISO is beyond me!
But even when downloading all of that and installing it properly I was still faced with this error when trying to setup the farm: “New-SPConfigurationDatabase : One or more types failed to load. Please refer to the upgrade log for more details.“. Going through the install log I found this: “SharePoint Foundation Upgrade SPSiteWssSequence ajywy ERROR Exception: Could not load file or assembly ‘Microsoft.Data.OData, Version=5.6.0.0, Culture=neutral, PublicKeyToken=31bc3856cd365e35’ or one of its dependencies. The system cannot find the file specified.

It seems that the WCF prerequisite file when installed using the Powershell method of manually downloading and installing it! Fortunately the quick fix is to find the file “WcfDataServices.exe” in your profile directory (i.e NOT the one you downloaded!), running it and choosing “Repair”. Only then did SharePoint 2016 install properly!

Enable Versioning On Entire SharePoint 2013 Application

SCENARIO
For some reason, probably money, you can’t use a proper backup solution for your farm. So you want to use versioning as a cheap mans backup.

PROBLEM
Going through every document library in every site in every site collection in every application to enable versioning isn’t possible. And there is no way to specify in Central Administration or declare a policy to enforce this.

SOLUTION
This powershell script will do the trick for you. It’s written to enabling versioning for an entire web application (with easy alteration it can be scoped to a specific site/site collection). What’s neat about this is that it will not change settings on the document libraries that already have it enabled! It will not enable minor versioning, but you can just enable that if you want.

As always, use on your own risk and test in a test environment first and then scope it to a test site collection in production farm!!

Add-PSSnapin Microsoft.SharePoint.PowerShell -erroraction SilentlyContinue
$webapp = "ENTER URL TO WEB APPLICATION"
$site = get-spsite -Limit All -WebApplication $WebApp
foreach($web in $site.AllWebs)
{
    Write-Host "Inspecting " $web.Title
    foreach ($list in $web.Lists)
    {
        if($list.BaseType -eq "DocumentLibrary")
        {
            $liburl = $webapp + $list.DefaultViewUrl
            Write-Host "Library: " $liburl
            Write-Host "Versioning enabled: " $list.EnableVersioning
            Write-Host "MinorVersioning Enabled: " $list.EnableMinorVersions
            Write-Host "EnableModeration: " $list.EnableModeration
            Write-Host "Major Versions: " $list.MajorVersionLimit
            Write-Host "Minor Versions: " $list.MajorWithMinorVersionsLimit
            $host.UI.WriteLine()
            if(!$list.EnableVersioning)
            {
                $list.EnableVersioning = $true
                $list.EnableMinorVersions = $false     # Set this to true if you want to enable minor versioning
                #$list.MajorVersionLimit = 10          # Remove comment hashtag and set this to the max amount of major versions you want
                #$list.MajorWithMinorVersionsLimit = 5 # Remove comment hashtag and set this to the max amount of minor versions you want
                $list.Update()
            }
        }
    }
}

Credit goes to Amrita Talreja @ HCL for this post which is the basis for this Powershell script.

SharePoint 2013 error “Exception from HRESULT: 0x80131401”

SCENARIO
After patching a SharePoint server with normal OS patches and reboot you are no longer able to browse to the applications or Central Admin. When looking at the log you see this error from C2WTS:
“An exception occurred when trying to issue security token: Loading this assembly would produce a different grant set from other instances. (Exception from HRESULT: 0x80131401).”
This was on a normal SharePoint Foundation 2013 server (build 15.0.4569.1506)

PROBLEM
If you check this TechNet forum post it seems to be related to “third party monitoring tools”. Unfortunately, SCOM is considered a third party tool in this case. And as it happens, we have just upgraded to SCOM2016!

SOLUTION
According to the TechNet forum post (and this official MS post) you should update or disable any third party monitoring tool. So, uninstalling the SCOM monitoring agent, rebooting, reinstalling it with “NOAPM=1” parameter will solve the issue (atleast it did for me).
However, if that it not an option (sometimes you can’t just reboot a critical server!), disabling Load Optimization does work, even if means your SharePoint is now unsupported. So I’m posting this for all us “it needs to be fixed now and I can’t find, update or disable whatever DLL is causing this!”-techies! So setting these registry keys works:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework, create a new ‘DWORD (32-bit) Value’ named “LoaderOptimization” with a value of “1”.
HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\.NETFramework, create a new ‘DWORD (32-bit) Value’ named “LoaderOptimization” with a value of “1”.

But as those MS people will tell you, it really isn’t a recommended solution (which is weird since it originated from MS support!).