Scenario

Every once in a while I would have the Forefront Antivirus for SharePoint engine on 1 of my 3 WFE’s conk out. When this happens, SharePoint is fully functional via that WFE except for file uploads which would cause users to experience an error message. This error would prevent the users from uploading any files via that WFE.

Error Messages

The end users uploading the files may experience the following error message:

“The installed virus scanner is currently unavailable. If the problem persists, contact your administrator.”

The Event Viewer Logs may show:

1719104822: #960013: Antivirus scanner timed out.

The SharePoint service is running but the Forefront VSAPI Library is not registered.

Manual Solution

The manual solution is to perform the procedure as described here by Ingo Karstein.

My Automated Solution

At first, I thought it would be a good idea to leverage my existing Diagnostics Log Monitoring script to check for the error messages. But after testing it out, I realized that the error entries would only be logged after a user had unsuccessfully tried to upload a document. After pondering for a bit, I wanted a way to prevent users from getting their uploads denied in the first place. So I ended up creating another script that auto-uploads a 1KB test document from each WFE and assumes that any upload error would have been caused by a hung Forefront service. The following PowerShell script was placed on each WFE and runs on a 5-minute interval. Upon an upload exception, it will disable the antivirus settings in Central Administration, restart the appropriate Windows Services, and then reinstate the Central Admin settings all with minimal service interruption. In testing, this automated process took between 5-10 seconds to run upon identification of an error. No IIS resets are performed during this process so the end-users wouldn’t even know that anything’s going on unless they happen to be trying to upload something right after Forefront hangs and  before the automated job runs every 5 minutes.

PowerShell Script

############# Start Variables ################
$uploadSite = "https://SharePointSite/"
$documentLibName = "Documents"
$testFile = "D:\Temp\TestUpload.txt"
$emailFrom = fromEmail
$emailTo = @("yourEmail")
$subject = "Forefront Failure; Auto-Kick Start Initiated"
$body = "Server: " + $env:COMPUTERNAME
$smtpserver = "yourSMTPServer"
$foreFrontDirectory = "C:\Program Files\Microsoft Forefront Protection for SharePoint\"
############# End Variables ##################

####### Start create test file if it doesn't exist
if(!(Test-Path -Path $testFile))
{
new-item -Path $testFile -Value "." –itemtype file
}
####### End create test file if it doesn't exist

[System.Reflection.Assembly]::LoadWithPartialName("Microsoft.SharePoint")
$site = New-Object microsoft.sharepoint.spsite($uploadSite)
$web = $site.openweb()
$library = $web.GetFolder($documentLibName)

$filestream = ([System.IO.FileInfo] (Get-Item $testFile)).openread()
$bytes = new-object byte[] $filestream.length
$filestream.read($bytes, 0, $filestream.length)
$filestream.close()
$folderPath = $library.URL + "/AutomatedTestUpload - $env:COMPUTERNAME.txt"

try
{
$library.files.add($folderPath, $bytes, $true)
}
catch [Exception]
{
$CAService = [Microsoft.SharePoint.Administration.SPWebService]::ContentService
$CAService.AntivirusSettings.UploadScanEnabled = $false
$CAService.AntivirusSettings.CleaningEnabled = $false
$CAService.Update()

Stop-Service -Displayname "Microsoft Forefront Server Protection Controller"
Stop-Service -DisplayName "Microsoft Forefront Server Protection Controller for SharePoint"
& ($foreFrontDirectory + "fsccontroller.exe") " /disable"
& ($foreFrontDirectory + "fsccontroller.exe") " /enable"

Restart-Service -DisplayName "SharePoint 2010 Administration"
Restart-Service -DisplayName "SharePoint 2010 Timer"

 Start-Service -DisplayName "Microsoft Forefront Server Protection Controller for SharePoint"
Start-Service -Displayname "Microsoft Forefront Server Protection Controller"

$CAService.AntivirusSettings.UploadScanEnabled = $true
$CAService.AntivirusSettings.CleaningEnabled = $true
$CAService.Update()

  Send-MailMessage -To $emailTo -Subject "Forefront Antivirus Auto-Kicked" -Body $body -SmtpServer $smtpserver -From $emailFrom -BodyAsHtml
}

$web.dispose()
$site.dispose()

Helpful Resources

http://ikarstein.wordpress.com/2010/12/07/forefront-protection-2010-for-sharepointerror-the-sharepoint-service-is-running-but-the-forefront-vsapi-library-is-not-registered/

http://ystex.net/2010/12/12/powershell-fun-setting-sharepoint-antivirus-settings/

Advertisements