PowerShell Script for Recreating the Server Cache (related to error in Windows Event Log, Event ID 6482: Application Server Administration job failed for service instance Microsoft.Office.Server.Search.Administration.SearchServiceInstance)

Today I’ve had the error:

Application Server Administration job failed for service instance Microsoft.Office.Server.Search.Administration.SearchServiceInstance (150CA1DD-02E3-47C0-AA55-005A2927751F).

Reason: An update conflict has occurred, and you must re-try this action. The object SearchDataAccessServiceInstance was updated by DOMAINspfarm, in the OWSTIMER (5040) process, on machine sps2010. 
View the tracing log for more information about the conflict.

Technical Support Details:
Microsoft.SharePoint.Administration.SPUpdatedConcurrencyException: An update conflict has occurred, and you must re-try this action.
The object SearchDataAccessServiceInstance was updated by domainuser, in the OWSTIMER (5040) process, on machine (server name). 
View the tracing log for more information about the conflict.
   at Microsoft.Office.Server.Search.Administration.SearchServiceInstance.Synchronize()
   at Microsoft.Office.Server.Administration.ApplicationServerJob.ProvisionLocalSharedServiceInstances(Boolean isAdministrationServiceJob)

 

There is a nice article on Jeff DeVerter’s blog:

Jeff references to this articles:

I had to clean up lots of servers. Because of that I’ve created a little PowerShell script.

The script will automatically process all steps descripted by the KB article, Chaitu Madala and Jeff.

You can execute the script on every server.

If your receive a yellow message at the end of the process that the resulting “cache.ini” file is diffrent from the original one. I think the cache.ini file contains a timestamp and it is OK if the new timestamp value is greater than the original one… But you use the script at your own rist – as always.

 

SCRIPT:

# Script created by Ingo Karstein (https://blog.kenaro.com)
Write-Host "Script created by Ingo Karstein (https://blog.kenaro.com)" -ForegroundColor DarkGreen

$cacheFolderRoot = Join-Path ${env:ProgramData} "MicrosoftSharePointConfig"
$cacheFileCopy = Join-Path ${env:temp} "cacheFileTmp.ini.ik"

Write-Host "" -ForegroundColor DarkBlue
Write-Host "Starting" -ForegroundColor DarkBlue

if( Test-Path $cacheFileCopy -PathType Leaf) {
    write-host "Cache File copy lopcation does already exist. Please remove it: $($cacheFileCopy)" -ForegroundColor Red
    return
}

Write-Host "Looking for cache folder" -ForegroundColor DarkBlue
$cacheFolder =  @(GEt-ChildItem -Path $cacheFolderRoot | ? {Test-Path $_.FullName -PathType Container} | ? {Test-Path -Path (Join-Path $_.FullName "cache.ini") -PathType Leaf})

if( $cacheFolder -ne $null -and $cacheFolder.Count -eq 1) {
    $cacheFolder0 = $cacheFolder[0].FullName
    Write-Host "Cache folder found: $($cacheFolder0)" -ForegroundColor DarkBlue
    $cacheFile = join-path $cacheFolder0 "cache.ini"
    Write-Host "Cache ini file: $($cacheFile)" -ForegroundColor DarkBlue

    Write-Host "Stop SharePoint timer service" -ForegroundColor DarkBlue
    stop-service sptimerv4

    Write-Host "Copy cache.ini to it's temp location ($($cacheFileCopy))" -ForegroundColor DarkBlue
    copy-item -path $cacheFile -Destination $cacheFileCopy -force

    Write-Host "Set the content of cache.ini to ""1""" -ForegroundColor DarkBlue
    "1" | set-content $cacheFile -encoding ascii -force

    Write-Host "Remove all .XML files from the cache folder" -ForegroundColor DarkBlue
    get-childitem $cacheFolder0 -filter "*.xml" | remove-item -force -confirm:$false

    Write-Host "Start SharePoint timer service" -ForegroundColor DarkBlue
    start-service sptimerv4

    $xmlFound = -1
    $xmlFoundLast = -1
    $eqCount = 0

    Write-Host "Now the cache will be recreated... Waiting... This will take a minute or so..." -ForegroundColor DarkBlue
    write-host "(every second a dot will appear on the end of the next line)" -ForegroundColor gray
    do {
        write-host "." -nonewline -ForegroundColor Magenta
        start-sleep -second 1
        $xmlFoundLast = $xmlFound
        $xmlFound = (@(get-childitem $cacheFolder0 -filter "*.xml")).Count
        if( $xmlFound -eq $xmlFoundLast ) {
            $eqCount++
        } else {
            $eqCount = 0
        }
    } while ($eqCount -lt 30)
    
    Write-Host ""
    Write-Host "Done" -ForegroundColor DarkBlue

    $a = get-content $cacheFileCopy
    $b = get-content $cacheFile

    if( $a -ne $b ) {
        if( [int]$a -gt [int]$b ) {
            write-host "An error occured. the content of the cache file is not identically to it's value before processing." -ForegroundColor Red
            write-host "Old: $($a)"
            write-host "New: $($b)"    
        } else {
            write-host "MAYBE an error occured. the content of the cache file is not identically to it's value before processing." -ForegroundColor DarkYellow
            write-host "Old: $($a)"
            write-host "New: $($b)"    
        }
    } else {
        write-host "Processing finished successfully! You need to execute the  script on every server!!" -foregroundcolor darkgreen
        remove-item $cacheFileCopy -Force -confirm:$false
    }
} else {
    write-host "Could not find the cache folder or found too much cache folders!" -foregroundcolor red
}