Script a Metadata Service Application using PowerShell

How To Create Manged Meta Data Service Application Using PowerShell

This how-to topic describes the steps required to create a Managed MetaData Service Application in sharepoint 2010 using powershell.One can create the managed metadata service application using the central admin manually. But when it comes to auto deployment and in production the manuel configuration is not the viable solution. Powershell helps to create this service application automatically. Also we can add the administrator rights to the Managed Meta Data Service.

The Solution Consist of many PowerShell files

My solution consist on many PowerShell files and single configuration file. the configuration file contains the token which is used in the PowerShell functions.
The solution consist of the following files.

In my solution we are trying to keep my service application related function in a separate PowerShell file. So that if one have to create multiple service application we can create one for each. For example service application for search. Search.ps1. and we can keep them also function folder. The structure of the files is described below. One need to just execute Deploy.ps1 which in turn will call Functions.ps1 and CustomFunctions.ps1 and other service application function which will create the service application.  Before executing the Deploy.ps1 ensure the parameters are configured properly in the Configuration file. Also the results will be captured and logged in the logs folder one for each service application.

  • Deploy.ps1
  • Function --> CustomFunctions.ps1, ManagedMetadataService.ps1
  • Configuration --> Config.xml
  • Logs 

Managed Metadata Service

  • Configure The below parameters used in creating the ManagedMetaData service.

    <ServiceName Value="Managed Metadata Application Name"/>
    <DatabaseName Value="DB_MMS_Service"/>
    <AppPoolName Value="Service ApplicationsAppPool"/>
    <AppPoolAccount Value="domain\username" />
    <ManagedServiceAcc Value="domain\AdminUserName" />
    <Servers>machinename</Servers>
    

Example PowerShell Script to Create the Managed MetaData Service

Function StartMMSService            
{            
# Get the XML file            
$file = ".\Configuration\Config.xml"            
            
Write-Host "Parsing file: $file`r`n"             
[xml]$XmlDoc = get-content $file            
            
# Retrieve Service Configuration From the Config File            
$sa_name = $XmlDoc.Services.MMSService.ServiceName.Value            
# Construct the Service Application Proxy Name - Based on Name            
# contained in $sa_name with Proxy added as a suffix            
$sa_proxy = $sa_name + " Proxy"            
$sa_dbname = $XmlDoc.Services.MMSService.DatabaseName.Value            
$sa_apppool = $XmlDoc.Services.MMSService.AppPoolName.Value            
$sa_apppoolac = $XmlDoc.Services.MMSService.AppPoolAccount.Value            
$sa_setupac = $XmlDoc.Services.MMSService.ManagedServiceAcc.Value            
$sa_servers = $XmlDoc.Services.MMSService.Servers            
            
# Commence Provisioning Process for MMS Service            
Write-Host "Provisioning Managed Metadata Service Service Application`r`n"            
Write-Host "`r`n"            
Write-Host "Service Application Parameters:`r`n"            
Write-Host "  Service Application Name            : $sa_name`r`n"            
Write-Host "  Service Application Proxy Name      : $sa_proxy`r`n"            
Write-Host "  Service Application Database Prefix : $sa_dbname`r`n"            
Write-Host "  Service Application Pool Name       : $sa_apppool`r`n"            
Write-Host "  Service Application Pool Account    : $sa_apppoolac`r`n"            
Write-Host "  Managed Service Account
 : $sa_setupac`r`n"            
Write-Host "`r`n"            
Write-Host "Service Instance Servers:`r`n"            
ForEach ($server In $sa_servers -Split ";")            
{            
# Write Out Each Server contained in the Config file            
Write-Host "  Destination Server : $server`r`n"            
}            
            
Write-Host "`r`n"            
            
# Determine if the Service Application has already been provisioned            
Write-Host "Verifying Managed Metadata Service Application Does NOT Already Exist...`r`n"            
Write-Host "`r`n"            
$sa = Get-SPServiceApplication | Where-Object {$_.Name -eq $sa_name}            
if ($sa -eq $null)            
{            
# We were unable to verify the existence of the Service Application, so we            
# need to proceed with the creation            
Write-Host "Unable to Verify Existence of Managed Metadata Service Service Application - Proceeding With Creation...`r`n"            
Write-Host "`r`n"            
            
# We need to see if the Application Pool exists before we attempt to provision the service            
Write-Host "Verifying Existence of Application Pool ($sa_apppool)...`r`n"            
Write-Host "`r`n"            
$ap = Get-SPServiceApplicationPool | Where-Object {$_.name -eq $sa_apppool}            
if ($ap -eq $null)            
{            
# We were unable to verify the application pool, so we need to create it            
Write-Host "Unable to Verify Existence of Application Pool - Creating Application Pool...`r`n"            
Write-Host "`r`n"            
            
# First we need to check for the presence of the Managed Account            
Write-Host "Verifying Existence of Managed Account ($sa_apppoolac)...`r`n"            
Write-Host "`r`n"            
$ma = Get-SPManagedAccount $sa_apppoolac -ErrorAction SilentlyContinue            
if ($ma -eq $null)            
{            
# We were unable to locate the Managed Account, so we need to flag this and then drop out            
Write-Host "Unable to Verify Existence of Managed Account - Unable to Proceed With MMS Provisioing...`r`n"            
Write-Host "`r`n"            
return            
}            
else            
{            
# We were able to verify the Managed Account, so we can proceed with creating the Application Pool            
Write-Host "Verified Existence of Managed Account - Proceeding With Application Pool Creation...`r`n"            
Write-Host "`r`n"            
$ap = New-SPServiceApplicationPool -Name $sa_apppool -Account $sa_apppoolac            
            
# Now we need to verify the existence of the Application Pool before proceeding            
if ($ap -eq $null)            
{            
# We were unable to create the Application Pool, so we need to flag this and then drop out            
Write-Host "Unable to Create Application Pool - Unable to Proceed With MMS Provisioning...`r`n"            
Write-Host "`r`n"            
return            
}            
}            
}            
            
# We were able to create the Application Pool, so we can proceed with creation of the Service Application            
Write-Host "Verified Application Pool Creation - Creating Service Application...`r`n"            
Write-Host "`r`n"            
$sa = New-SPMetadataServiceApplication -Name $sa_name -ApplicationPool $ap -DatabaseName $sa_dbname            
            
# Now that we have created the Service Application, we need to create the associated proxy            
if ($sa -eq $null)            
{            
# We Were unable to create the Service Application            
Write-Host "Service Application Creation Failed - Unable to Proceed With MMS Proxy Configuration...`r`n"            
Write-Host "`r`n"            
return            
}            
else            
{            
# We were able to create the Service Application, so we can proceed with creation of the Proxy...            
Write-Host "Verified Creation of Service Application - Provisioning MMS Proxy...`r`n"            
Write-Host "`r`n"            
$sapxy = New-SPMetadataServiceApplicationProxy -Name $sa_proxy -ServiceApplication $sa -DefaultProxyGroup            
}            
}            
else            
{            
# We have been able to verify the existence of the Service Application, so            
# we can skip creation            
Write-Host "Managed Metadata Service Service Application Already Exists - Skipping Provisioning...`r`n"            
Write-Host "`r`n"            
}            
            
# Now that the Service Application has been provisioned, we need to start the instances on the            
# specified servers            
ForEach ($server In $sa_servers -Split ";")            
{            
Write-Host "Verifying Managed Metadata Service State On Server : $server...`r`n"            
Write-Host ""            
$svc = Get-SPServiceInstance -Server $server | Where {$_.TypeName -eq "Managed Metadata Web Service"}            
If ($svc.Status -ne "Online")            
{            
# The service instance is currently stopped, so we need to configure and start the instance on the            
# appropriate server            
Write-Host "Managed Metadata Service NOT Started on Server : $server - Starting Service...`r`n"            
Write-Host "`r`n"            
Start-SPServiceInstance $svc            
}            
}            
            
# Managed Metadata Service Application Provisioning Completed            
Write-Host "Managed Metadata Service Application Provisioning Completed`r`n"            
Write-Host "`r`n"            
            
# Managed Metadata Service - assigning admin account            
Write-Host "Managed Metadata Service - Assigning admin account `r`n"            
Write-Host "`r`n"            
AssignServiceAdmin($sa.ID, $sa_setupac)            
}            
            
            
* I had kept AssignServiceAdmin function in a separate PowerShell file called CustomFunctions.ps1.            
            
function AssignServiceAdmin($params)            
{            
Write-Host "Entry: AssignServiceAdmin `r`n"            
Write-Host "Parms " $params "`r`n"            
            
$ServiceAppId = $params[0]            
$AccountName = $params[1]            
Write-Host "Service app id = " $ServiceAppId "`r`n"            
Write-Host "AccountName = " $AccountName "`r`n"            
            
Write-Host "Getting a reference to the Service App `r`n"            
$mms = Get-SPServiceApplication | where-object {$_.ID -eq $ServiceAppId }            
#$mms = Get-SPServiceApplication $ServiceAppId            
            
Write-Host "Pulling the Security object from it.`r`n"            
$serviceAppSecurity = $mms.GetAdministrationAccessControl();            
            
Write-Host "Creating Farm object....`r`n"            
$spFarm = [Microsoft.SharePoint.Administration.SPFarm]::Local             
            
Write-Host "Creating Claim Provider Manager....`r`n"            
$mgr = [Microsoft.SharePoint.Administration.Claims.SPClaimProviderManager]::Local             
            
Write-Host "Creating claim for " $AccountName "`r`n"            
$claim = $mgr.ConvertIdentifierToClaim($AccountName, [Microsoft.SharePoint.Administration.Claims.SPIdentifierTypes]::WindowsSamAccountName)            
            
Write-Host "Creating access rule object `r`n"            
$spAclAccessRule = [Microsoft.SharePoint.Administration.AccessControl.SPAclAccessRule``1]            
            
Write-Host "Creating CA rights object `r`n"            
$SPCAAppRights = [Microsoft.SharePoint.Administration.AccessControl.SPCentralAdministrationRights]            
            
Write-Host "Making an acl access rule `r`n"            
$aclAccessRule = $spAclAccessRule.MakeGenericType($SPCAAppRights)             
            
Write-Host "Creating a full control access rule `r`n"            
$actualAccessRule = New-Object($AclAccessRule) $claim, "FullControl"             
            
Write-Host "Adding the rule to the MMS service app `r`n"            
$serviceAppSecurity.AddAccessRule($actualAccessRule)            
            
Write-Host "Updating the MMS app now... `r`n"            
$mms.SetAdministrationAccessControl($serviceAppSecurity)             
$mms.Uncache()            
            
# Now check to see if it has been added            
$adminAcl = $serviceAppSecurity.ToAcl();            
foreach ($rights in $adminAcl)            
{            
Write-Host "Rights for name: " $rights.DisplayName "`r`n"            
Write-Host "Rights for Principlename: " $rights.PrincipleName "`r`n"            
Write-Host "GrantRightsMask: " $rights.GrantRightsMask "`r`n"            
Write-Host "DenyRightsMask: " $rights.DenyRightsMask "`r`n"            
Write-Host "IsWindowsAuthenticationMode: " $rights.IsWindowsAuthenticationMode "`r`n"            
}            
}            
            
            
* Please ensure SharePoint Snapin has been loaded before executing the above scripts. One can call the StartMMSService function from the deploy.ps1. I had separated the calling function in separate powershell file so that if we want to create multiple service application we can do it one after other. One can use below function to check sharepoint snapin is added or not.            
            
            
# Checks to ensure that the SharePoint Snapin has been loaded.            
# Loads the snapin if it is not present.            
function Check-SPTSnapIn            
{            
Write-Host "Detecting SharePoint SnapIn.  Please wait..."            
Write-Host ""            
            
$sp = get-pssnapin | where-object {$_.name -eq "Microsoft.SharePoint.PowerShell"}            
            
if ($sp -eq $null)            
{            
# Unable to detect the SharePoint SnapIn, so we need to load it...            
Write-Host "SharePoint SnapIn NOT detected - Loading SharePoint SnapIn.  Please wait..."            
Write-Host ""            
            
# Load the SnapIn            
add-pssnapin "Microsoft.SharePoint.PowerShell"            
            
# Perform a final check to ensure that the snapin was successfully loaded
            
$sp = get-pssnapin | where-object {$_.name -eq "Microsoft.SharePoint.PowerShell"}            
if ($sp -eq $null)            
{            
# Unable to verify successful load of snapin - report failure            
# drop out            
Write-Host "Unable to verify successful load of SnapIn"            
Write-Host ""            
}            
else            
{            
# Able to verify successful load of snapin            
Write-Host "SnapIn Load Verified"            
Write-Host ""            
}            
}            
else            
{            
# We were able to detect the SharePoint SnapIn            
Write-Host "SharePoint SnapIn Detected"            
Write-Host ""            
}            
}

The Logs for result or error in logged in the InstallLog folder under the seprate log file for each service.

Verification steps to check whether the managed MetaData service is created successully or not. Go to Central Admin under application Management. Click on Manage Service Application. Please check the the Managed Meta Data service application is created with the name you had configured it in config file.

Please email me for the full working code.