janikvonrotz
2/7/2014 - 1:02 PM

PowerShell: Install SharePoint 2013 #PowerShell #SharePoint #CompanyIOZ

PowerShell: Install SharePoint 2013 #PowerShell #SharePoint #CompanyIOZ

#Mit Hilfe von diesem Script kann die SharePoint Konfiguration abgeschlossen werden
#Alle Punkte welche benötigt werden, selectiv ausführen

#Start Schritt 1
$snapin = Get-PSSnapin Microsoft.SharePoint.Powershell -ErrorVariable err -ErrorAction SilentlyContinue
if($snapin -eq $null){
Add-PSSnapin Microsoft.SharePoint.Powershell 
}
#Stop Schritt 1

#Berechtigungen setzen, damit alle Services richtig funktionieren
#----------------------------------------------------------------

#Berechtigung für Work Management Service
$WebApp = Get-SPWebApplication -Identity https://mysite.xyz.ch #MySite ULR
$WebApp.GrantAccessToProcessIdentity("DOMAIN\sa-spservices")

#Berechtigung für Visio und Excel Services
$WebApp = Get-SPWebApplication -Identity https://abc.xyz.ch #Intranet oder andere WebApp
$WebApp.GrantAccessToProcessIdentity("DOMAIN\sa-spservices")

#Berechtigung für MySite Newsfeed
$WebApp = Get-SPWebApplication -Identity https://mysite.xyz.ch #MySite ULR
$WebApp.GrantAccessToProcessIdentity("DOMAIN\sa-spintranet") #Service Account von Intranet oder anderer WebApp
$WebApp = Get-SPWebApplication -Identity https://abc.xyz.ch #Intranet oder andere WebApp
$WebApp.GrantAccessToProcessIdentity("DOMAIN\sa-spmysite") #Service Account von MySite


#Berechtingen setzen für HeatingUpScript (SharePointWarmUpHelper)
#----------------------------------------------------------------

#Set the HeatingUpScript Account to one WebApps
$userOrGroup = "DOMAIN\sa-spadmin" #Entsprechender Service Account, unter welchem das HeatingUpScript ausgeführt wird
$displayName = "HeatingUpScript Account" 

$webApp = Get-SPWebApplication -Identity "https://abc.xyz.ch"
$policy = $webApp.Policies.Add($userOrGroup, $displayName) 
$policyRole = $webApp.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullRead) 
$policy.PolicyRoleBindings.Add($policyRole) 
$webApp.Update() 

#For all WebApps
$userOrGroup = "DOMAIN\sa-spadmin" #Entsprechender Service Account, unter welchem das HeatingUpScript ausgeführt wird
$displayName = "HeatingUpScript Account" 
Get-SPWebApplication | foreach { 
    $webApp = $_ 
    $policy = $webApp.Policies.Add($userOrGroup, $displayName) 
    $policyRole = $webApp.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullControl) 
    $policy.PolicyRoleBindings.Add($policyRole) 
    $webApp.Update() 
}


#Berechtigung für Publishing Feater auf WebApp setzen (dies wird nur für SharePoint Server Standard/Enterprise benötigt)
#-----------------------------------------------------------------------------------------------------------------------

#Set the CacheSuperReader Account to one WebApps
$userOrGroup = "DOMAIN\SP_CacheSuperReader"
$displayName = "CacheSuperReader" 

$webApp = Get-SPWebApplication -Identity "https://abc.xyz.ch"
$policy = $webApp.Policies.Add($userOrGroup, $displayName) 
$policyRole = $webApp.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullRead) 
$policy.PolicyRoleBindings.Add($policyRole) 
$webApp.Update()

#Set the CacheSuperUser Account to one WebApps
$userOrGroup = "DOMAIN\SP_CacheSuperUser"
$displayName = "CacheSuperUser" 

$webApp = Get-SPWebApplication -Identity "https://abc.xyz.ch"
$policy = $webApp.Policies.Add($userOrGroup, $displayName) 
$policyRole = $webApp.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullControl) 
$policy.PolicyRoleBindings.Add($policyRole) 
$webApp.Update()


#Allow PDF to open direct in Browser (Permissive) inkl. RecycleBin auf 40 Tage setzen
#------------------------------------------------------------------------------------
$webapps = Get-SPWebApplication
foreach ($webapp in $webapps) 
{ 
    $webapp.AllowedInlineDownloadedMimeTypes.Add("application/pdf") 
    $webapp.RecycleBinRetentionPeriod = 40
    $webapp.Update() 
}


#Healt Roles Disablen
#--------------------
#The server farm account should not be used for other services
Disable-SPHealthAnalysisRule -Identity 'FarmAccountIsSharedWithUserServices' -Confirm:$false
#Databases exist on servers running SharePoint Foundation
Disable-SPHealthAnalysisRule -Identity 'DatabasesAreOnAppServers' -Confirm:$false
#Database has large amounts of unused space
Disable-SPHealthAnalysisRule -Identity 'DatabaseCanBeShrinked' -Confirm:$false
#Built-in accounts are used as application pool or service identities
Disable-SPHealthAnalysisRule -Identity 'BuiltInAccountsUsedAsProcessIdentities' -Confirm:$false
#Accounts used by application pools or services identities are in the local ma-chine Administrators group
Disable-SPHealthAnalysisRule -Identity 'AdminAccountsUsedAsProcessIdentities' -Confirm:$false
#Drives are at risk of running out of free space. 
Disable-SPHealthAnalysisRule -Identity 'AppServerDrivesAreNearlyFullWarning' -Confirm:$false

Get-SPHealthAnalysisRule | where {!$_.Enabled} | select Summary


#Set Log Settings
#----------------
Set-SPLogLevel -TraceSeverity Unexpected
Set-SPLogLevel -EventSeverity ErrorCritical
Set-SPDiagnosticConfig -LogLocation "D:\Microsoft Office Servers\15.0\Logs" 
Set-SPDiagnosticConfig -LogMaxDiskSpaceUsageEnabled
Set-SPDiagnosticConfig -LogDiskSpaceUsageGB 1


# Minimal Download Strategy (MDS) Für alle Sites in allen WebApplications deaktivieren
#----------------------------------------
$snapin = Get-PSSnapin Microsoft.SharePoint.Powershell -ErrorVariable err -ErrorAction SilentlyContinue
if($snapin -eq $null){
Add-PSSnapin Microsoft.SharePoint.Powershell 
}
# Get All Web Applications
$WebApps=Get-SPWebApplication
foreach($webApp in $WebApps)
{
    foreach ($SPsite in $webApp.Sites)
    {
       # get the collection of webs
       foreach($SPweb in $SPsite.AllWebs)
        {
        $feature = Get-SPFeature -Web $SPweb | Where-Object {$_.DisplayName -eq "MDSFeature"}
        if ($feature -eq $null)
            {
                Write-Host -ForegroundColor Yellow 'MDS already disabled on site : ' $SPweb.title ":" $spweb.URL;
            }
        else
            {
                Write-Host -ForegroundColor Green 'Disable MDS on site : ' $SPweb.title ":" $spweb.URL;
                Disable-SPFeature MDSFeature -url $spweb.URL -Confirm:$false
            }
        }
    }
}


#Office Web Apps Bindings
#------------------------
New-SPWOPIBinding –ServerName officewebapps.xyz.ch
Set-SPWopiZone –Zone “internal-https”


#Neue WebApp inkl. Extend
#------------------------

#New WebApp (with HostHeader)
$webappname = "SP_XYZ"
$webappaccount = "DOMAIN\sa-spxyz" #have to be managed account
$spadmin = "DOMAIN\sa-spadmin"
$webappport = "443"
$webappurl = "https://abc.xyz.ch"
$hostheader = "abc.xyz.ch"
$webSitePfad = "D:\wea\webs\SP_XYZ"
$dbserver = "SQLALIAS"
$webappdbname = "SP_Content_XYZ"
$ap = New-SPAuthenticationProvider
$rootsitename = "XYZ"
$templatename = "STS#0" #Team Site
$lcid = "1031" # 1031 Deutsch; 1033 English; 1036 French; 1040 Italian

New-SPWebApplication -Name $webappname -SecureSocketsLayer -ApplicationPool $webappname -ApplicationPoolAccount (Get-SPManagedAccount $webappaccount) -Port $webappport -Url $webappurl -Path $webSitePfad  -DatabaseServer $dbserver -DatabaseName $webappdbname -AuthenticationProvider $ap -HostHeader $hostheader -Verbose
New-SPSite -url $webappurl -OwnerAlias $webappaccount -SecondaryOwnerAlias $spadmin -Name $rootsitename -Template $templatename -language $lcid | Out-Null
Start-Process "$webappurl" -WindowStyle Minimized

#Extend WebApp
$webappurl = "https://abc.xyz.ch"
$ExtendName = "SP_XYZ_80"
$ExtendPath = "D:\wea\webs\SP_XYZ_80"
$Extendhostheader = "abc.xyz.ch"
$ExtendZone = "Intranet"
$ExtendURL = "http://abc.xyz.ch"
$ExtPort = "80"
$ntlm = New-SPAuthenticationProvider -UseWindowsIntegratedAuthentication -DisableKerberos 
Get-SPWebApplication -Identity $webappurl | New-SPWebApplicationExtension -Name $ExtendName  -Zone $ExtendZone -URL $ExtendURL -Port $ExtPort -AuthenticationProvider $ntlm -Verbose -Path $ExtendPath -HostHeader $Extendhostheader


#Neue WebApp für MySite
#------------------------

#New WebApp (with HostHeader)
$webappname = "SP_MySite"
$webappaccount = "DOMAIN\sa-spmysite" #have to be managed account
$spadmin = "DOMAIN\sa-spadmin"
$webappport = "443"
$webappurl = "https://mysite.xyz.ch"
$hostheader = "mysite.xyz.ch"
$webSitePfad = "D:\wea\webs\SP_MySite"
$dbserver = "SQLALIAS"
$webappdbname = "SP_Content_MySite"
$ap = New-SPAuthenticationProvider
$rootsitename = "MySite Host"
$templatename = "SPSMSITEHOST#0" #Team Site
$lcid = "1031" # 1031 Deutsch; 1033 English; 1036 French; 1040 Italian

New-SPWebApplication -Name $webappname -SecureSocketsLayer -ApplicationPool $webappname -ApplicationPoolAccount (Get-SPManagedAccount $webappaccount) -Port $webappport -Url $webappurl -Path $webSitePfad  -DatabaseServer $dbserver -DatabaseName $webappdbname -AuthenticationProvider $ap -HostHeader $hostheader -Verbose
New-SPSite -url $webappurl -OwnerAlias $webappaccount -SecondaryOwnerAlias $spadmin -Name $rootsitename -Template $templatename -language $lcid | Out-Null
Start-Process "$webappurl" -WindowStyle Minimized

#Extend WebApp
$webappurl = "https://mysite.xyz.ch"
$ExtendName = "SP_MySite_80"
$ExtendPath = "D:\wea\webs\SP_MySite_80"
$Extendhostheader = "mysite.xyz.ch"
$ExtendZone = "Intranet"
$ExtendURL = "http://mysite.xyz.ch"
$ExtPort = "80"
$ntlm = New-SPAuthenticationProvider -UseWindowsIntegratedAuthentication -DisableKerberos 
Get-SPWebApplication -Identity $webappurl | New-SPWebApplicationExtension -Name $ExtendName  -Zone $ExtendZone -URL $ExtendURL -Port $ExtPort -AuthenticationProvider $ntlm -Verbose -Path $ExtendPath -HostHeader $Extendhostheader


#Set Content DB Limits
#---------------------
$dbs = Get-SPContentDatabase | where{$_.Name -ne "SP_Content_XYZ"}
foreach ($db in $dbs) {
    $db.MaximumSiteCount = 1
    $db.WarningSiteCount = 0
    $db.Update()
}


#Business Data Connectivity Service (BDC) Anpassungen
#----------------------------------------------------

#BDC - Enable revert to self
#Damit wird mit dem Service Account von der entsprechenden WebApp auf die Dritt-DB zugegriffen 
$bdc = Get-SPServiceApplication | where {$_ -match “Business Data Connectivity”};
$bdc.RevertToSelfAllowed = $true;
$bdc.Update();  


#Nach SharePoint Update werden folgende DB's nicht aktualisiert
#Mit folgendem Befehl können die DB's aktualisiert werden
#--------------------------------------------------------------- 

#BDC DB Update
(Get-SPDatabase | ?{$_.type -eq "Microsoft.SharePoint.BusinessData.SharedService.BdcServiceDatabase"}).Provision() 

#Secure Store DB Update
$db = (Get-SPDatabase | ?{$_.type -eq "Microsoft.Office.SecureStoreService.Server.SecureStoreServiceDatabase"}).Provision() 
$db.NeedsUpgrade


#Distributed Cache
#-----------------

#Check Cache Cluster Health
Use-CacheCluster
Get-CacheClusterHealth
Get-CacheHost

#Manueller Neustart vom Distributed Cache
Restart-CacheCluster
#Start Schritt 1
$snapin = Get-PSSnapin Microsoft.SharePoint.Powershell -ErrorVariable err -ErrorAction SilentlyContinue
if($snapin -eq $null){
Add-PSSnapin Microsoft.SharePoint.Powershell 
}

function Write-Info([string]$msg){
    Write-Host "$($global:indent)[$([System.DateTime]::Now)] $msg"
}

function Get-ConfigurationSettings() {
    Write-Info "Loading configuration file."
    [xml]$config = Get-Content .\Configurations.xml

    if ($? -eq $false) {
        Write-Info "Cannot load configuration source XML $config."
        return $null
    }
    return $config.Configurations
}

function Trace([string]$desc, $code) {
    trap {
        Write-Error $_.Exception
        if ($_.Exception.InnerException -ne $null) {
            Write-Error "Inner Exception: $($_.Exception.InnerException)"
        }
        break
    }
    $desc = $desc.TrimEnd(".")
    Write-Info "BEGIN: $desc..."
    Set-Indent 1
    &$code
    Set-Indent -1
    Write-Info "END: $desc."
}

function Set-Indent([int]$incrementLevel)
{
    if ($incrementLevel -eq 0) {$global:indent = ""; return}
    
    if ($incrementLevel -gt 0) {
        for ($i = 0; $i -lt $incrementLevel; $i++) {
            $global:indent = "$($global:indent)`t"
        }
    } else {
        if (($global:indent).Length + $incrementLevel -ge 0) {
            $global:indent = ($global:indent).Remove(($global:indent).Length + $incrementLevel, -$incrementLevel)
        } else {
            $global:indent = ""
        }
    }
}

#Region Security-Related
# ====================================================================================
# Func: Get-AdministratorsGroup
# Desc: Returns the actual (localized) name of the built-in Administrators group
# From: Proposed by Codeplex user Sheppounet at http://autospinstaller.codeplex.com/discussions/265749
# ====================================================================================
Function Get-AdministratorsGroup
{
    If(!$builtinAdminGroup)
    {
        $builtinAdminGroup = (Get-WmiObject -Class Win32_Group -computername $env:COMPUTERNAME -Filter "SID='S-1-5-32-544' AND LocalAccount='True'" -errorAction "Stop").Name
    }
    Return $builtinAdminGroup
}

#Region Add Managed Accounts
# ===================================================================================
# FUNC: AddManagedAccounts
# DESC: Adds existing accounts to SharePoint managed accounts and creates local profiles for each
# TODO: Make this more robust, prompt for blank values etc.
# ===================================================================================
Function AddManagedAccounts([System.Xml.XmlElement]$xmlinput)
{
    #WriteLine
    Write-Host -ForegroundColor White " - Adding Managed Accounts"
    If ($xmlinput.Accounts)
    {
        # Get the members of the local Administrators group
        $builtinAdminGroup = Get-AdministratorsGroup
        $adminGroup = ([ADSI]"WinNT://$env:COMPUTERNAME/$builtinAdminGroup,group")
        # This syntax comes from Ying Li (http://myitforum.com/cs2/blogs/yli628/archive/2007/08/30/powershell-script-to-add-remove-a-domain-user-to-the-local-administrators-group-on-a-remote-machine.aspx)
        $localAdmins = $adminGroup.psbase.invoke("Members") | ForEach-Object {$_.GetType().InvokeMember("Name", 'GetProperty', $null, $_, $null)}
        # Ensure Secondary Logon service is enabled and started
        If (!((Get-Service -Name seclogon).Status -eq "Running"))
        {
            Write-Host -ForegroundColor White " - Enabling Secondary Logon service..."
            Set-Service -Name seclogon -StartupType Manual
            Write-Host -ForegroundColor White " - Starting Secondary Logon service..."
            Start-Service -Name seclogon
        }

        ForEach ($account in $xmlinput.Accounts.Account)
        {
            $username = $account.name
            $password = $account.Password
            $password = ConvertTo-SecureString "$password" -AsPlaintext -Force
            # The following was suggested by Matthias Einig (http://www.codeplex.com/site/users/view/matein78)
            # And inspired by http://todd-carter.com/post/2010/05/03/Give-your-Application-Pool-Accounts-A-Profile.aspx & http://blog.brainlitter.com/archive/2010/06/08/how-to-revolve-event-id-1511-windows-cannot-find-the-local-profile-on-windows-server-2008.aspx
            Try
            {
                Write-Host -ForegroundColor White " - Creating local profile for $username..." -NoNewline
                $credAccount = New-Object System.Management.Automation.PsCredential $username,$password
                $managedAccountDomain,$managedAccountUser = $username -Split "\\"
                # Add managed account to local admins (very) temporarily so it can log in and create its profile
                If (!($localAdmins -contains $managedAccountUser))
                {
                    $builtinAdminGroup = Get-AdministratorsGroup
                    ([ADSI]"WinNT://$env:COMPUTERNAME/$builtinAdminGroup,group").Add("WinNT://$managedAccountDomain/$managedAccountUser")
                }
                Else
                {
                    $alreadyAdmin = $true
                }
                # Spawn a command window using the managed account's credentials, create the profile, and exit immediately
                Start-Process -WorkingDirectory "$env:SYSTEMROOT\System32\" -FilePath "cmd.exe" -ArgumentList "/C" -LoadUserProfile -NoNewWindow -Credential $credAccount
                # Remove managed account from local admins unless it was already there
                $builtinAdminGroup = Get-AdministratorsGroup
                If (-not $alreadyAdmin) {([ADSI]"WinNT://$env:COMPUTERNAME/$builtinAdminGroup,group").Remove("WinNT://$managedAccountDomain/$managedAccountUser")}
                Write-Host -BackgroundColor Blue -ForegroundColor Black "Done."
            }
            Catch
            {
                $_
                Write-Host -ForegroundColor White "."
                Write-Warning "Could not create local user profile for $username"
                break
            }
            $managedAccount = Get-SPManagedAccount | Where-Object {$_.UserName -eq $username}
            If ($managedAccount -eq $null)
            {
                Write-Host -ForegroundColor White " - Registering managed account $username..."
                If ($username -eq $null -or $password -eq $null)
                {
                    Write-Host -BackgroundColor Gray -ForegroundColor DarkBlue " - Prompting for Account: "
                    $credAccount = $host.ui.PromptForCredential("Managed Account", "Enter Account Credentials:", "", "NetBiosUserName" )
                }
                Else
                {
                    $credAccount = New-Object System.Management.Automation.PsCredential $username,$password
                }
                New-SPManagedAccount -Credential $credAccount | Out-Null
                If (-not $?) { Throw " - Failed to create managed account" }
            }
            Else
            {
                Write-Host -ForegroundColor White " - Managed account $username already exists."
            }
        }
    }
    Write-Host -ForegroundColor White " - Done Adding Managed Accounts"
    #WriteLine
}
#EndRegion

function Get-Account([System.Xml.XmlElement]$accountNode){
    while (![string]::IsNullOrEmpty($accountNode.Ref)) {
        $accountNode = $accountNode.PSBase.OwnerDocument.SelectSingleNode("//Accounts/Account[@ID='$($accountNode.Ref)']")
    }

    if ($accountNode.Password.Length -gt 0) {
        $accountCred = New-Object System.Management.Automation.PSCredential $accountNode.Name, (ConvertTo-SecureString $accountNode.Password -AsPlainText -force)
    } else {
        Write-Info "Please specify the credentials for" $accountNode.Name
        $accountCred = Get-Credential $accountNode.Name
    }
    return $accountCred    
}
 
function Get-InstallOnCurrentServer([System.Xml.XmlElement]$node) 
{
    if ($node -eq $null -or $node.Server -eq $null) {
        return $false
    }
    $dbserver = $node.Server | where { (Get-ServerName $_).ToLower() -eq $env:ComputerName.ToLower() }
    if ($dbserver -eq $null -or $dbserver.Count -eq 0) {
        return $false
    }
    return $true
}

function Get-ServerName([System.Xml.XmlElement]$node)
{
    while (![string]::IsNullOrEmpty($node.Ref)) {
        $node = $node.PSBase.OwnerDocument.SelectSingleNode("//Servers/Server[@ID='$($node.Ref)']")
    }
    if ($node -eq $null -or $node.Name -eq $null) { throw "Unable to locate server name!" }
    return $node.Name
}

[System.Xml.XmlElement]$config = Get-ConfigurationSettings

if ($config -eq $null) {
    return $false
}

#Variabeln
$dbserver = $config.Farm.DatabaseServer

AddManagedAccounts $config
#Stop Schritt 1

#Start Schritt 2
Trace "Configure WebApplication" {  
	foreach($item in $config.WebApplications.WebApplication){
		$webappname=$item.Name
	 	$webappport=$item.Port
        $rootsitename=$item.RootSiteName
        $webSitePfad=$item.WebSitePath + $webappname
        $webappdbname=$item.WebAppDBName
		$webappurl=$item.url
		$webappaccount=Get-Account($item.Account)
		$email = $config.email
		$lcid=$item.language
        $secondaryAdmin=$item.SecondaryAdmin
        $ap = New-SPAuthenticationProvider

		#New-SPManagedAccount -Credential $webappaccount
		
		if($webappport -eq "443"){
		   New-SPWebApplication -Name $webappname -SecureSocketsLayer -ApplicationPool $webappname -ApplicationPoolAccount (Get-SPManagedAccount $webappaccount.UserName) -Port $webappport -Url $webappurl -Path $webSitePfad  -DatabaseServer $dbserver -DatabaseName $webappdbname -AuthenticationProvider $ap | Out-Null
		   New-SPSite -url $webappurl -OwnerAlias $webappaccount.UserName -SecondaryOwnerAlias $secondaryAdmin -Name $rootsitename -OwnerEmail $email -Template "STS#0" -language $lcid | Out-Null
           Write-Host -ForegroundColor Yellow "Bind the coresponding SSL Certificate to the IIS WebSite"
           Start-Process "$webappurl" -WindowStyle Minimized
		}else{
	  	   New-SPWebApplication -Name $webappname -ApplicationPool $webappname -ApplicationPoolAccount (Get-SPManagedAccount $webappaccount.UserName) -Port $webappport -Url $webappurl -Path $webSitePfad -DatabaseServer $dbserver -DatabaseName $webappdbname -AuthenticationProvider $ap | Out-Null
		   New-SPSite -url $webappurl -OwnerAlias $webappaccount.UserName -SecondaryOwnerAlias $secondaryAdmin -Name $rootsitename -OwnerEmail $email -Template "STS#0" -language $lcid | Out-Null
           Start-Process "$webappurl" -WindowStyle Minimized
		}
   }
}
#Stop Schritt 2

#Start Schritt 3
Trace "Configure UsageApplicationService" { 
	try
	{
		Write-Host -ForegroundColor Yellow "- Creating WSS Usage Application..."
        New-SPUsageApplication -Name "Usage and Health data collection Service" -DatabaseServer $dbserver -DatabaseName $config.Services.UsageApplicationService.collectioDB | Out-Null
        Set-SPUsageService -LoggingEnabled 1 -UsageLogLocation $config.Services.UsageApplicationService.LogPfad
        $ua = Get-SPServiceApplicationProxy | where {$_.DisplayName -eq "Usage and Health data collection Service"}
        $ua.Provision()
	    Write-Host -ForegroundColor Yellow "- Done Creating WSS Usage Application."
	}
	catch
	{	Write-Output $_
	}
}

Trace "Incoming Email disable" {
    $incommingEmail = Get-SPServiceInstance | Where {$_.TypeName -eq "Microsoft SharePoint Foundation Incoming E-Mail"} 
    If ($incommingEmail.Status -eq "Online") 
    {
    	try
    	{
    		Write-Host "- Stoping Microsoft SharePoint Foundation Incoming E-Mail..."
    		$incommingEmail | Stop-SPServiceInstance -Confirm:$false | Out-Null
    		If (-not $?) {throw}
    	}
    	catch {"- Microsoft SharePoint Foundation Incoming E-Mail"}
    }
}

Trace "Microsoft SharePoint Foundation User Code Service" {
    $UserCodeService = Get-SPServiceInstance | Where {$_.TypeName -eq "Microsoft SharePoint Foundation Sandboxed Code Service"} 
    If ($UserCodeService.Status -eq "Disabled") 
    {
    	try
    	{
    		Write-Host "- Starting Microsoft SharePoint Foundation User Code Service..."
    		$UserCodeService | Start-SPServiceInstance | Out-Null
    		If (-not $?) {throw}
    	}
    	catch {"- An error occurred starting the Microsoft SharePoint Foundation User Code Service"}
    }
}

Trace "Configure State Service" { 
	try
	{
        Write-Host -ForegroundColor Yellow "Creating State Service Application..."
        New-SPStateServiceDatabase -name $config.Services.StateService.DBName | Out-Null
        New-SPStateServiceApplication -Name "State Service Application" -Database $config.Services.StateService.DBName  | Out-Null
        Get-SPStateServiceDatabase | Initialize-SPStateServiceDatabase | Out-Null
        Get-SPStateServiceApplication | New-SPStateServiceApplicationProxy -Name "State Service Application Proxy"  -DefaultProxyGroup | Out-Null
	    Write-Host -ForegroundColor Yellow "Done Creating State Service Application."
	}
	catch
	{	Write-Output $_
	}
}

Trace "Configure Search Service Application" { 
	try
	{
        #Get ServerName
        $searchServerName= $config.Servers.Server.Name

        #Create an Empty Direcotry for the Index
        $IndexLocation=$config.Services.EnterpriseSearch.IndexLocation
        New-Item $IndexLocation -type directory
        if(Test-Path $IndexLocation!=true){
            Write-Host -ForegroundColor Yellow "Create an Empty Index Direcotry Index under D:\Microsoft Office Servers\15.0\Data\Office Server\Applications"
            exit
        }        

        #Start earchService and SearchQueryAndSiteSettingsService Instances
        Start-SPEnterpriseSearchServiceInstance $searchServerName
        Start-SPEnterpriseSearchQueryAndSiteSettingsServiceInstance $searchServerName

        sleep 60

		Write-Host -ForegroundColor Yellow "- Creating Search Application Pool"
        $app = Get-SPServiceApplicationPool -Identity $config.Services.EnterpriseSearch.AppPoolName -ErrorVariable err -ErrorAction SilentlyContinue
        if($app.Name -eq $null){
            $appoolname=$config.Services.EnterpriseSearch.AppPoolName
    		$appooluser=Get-Account($config.Services.EnterpriseSearch.Account[0])
            $app = New-SPServiceApplicationPool -name $appoolname -account (Get-SPManagedAccount $appooluser.username) 
        }

        Write-Host -ForegroundColor Yellow "- Creating Search Application"
        $searchapp = New-SPEnterpriseSearchServiceApplication  -name "Search Service Application" -ApplicationPool $app -databaseName  $config.Services.EnterpriseSearch.DBName -DatabaseServer $dbserver
        $proxy = New-SPEnterpriseSearchServiceApplicationProxy -name "Search Service Application Proxy" -SearchApplication "Search Service Application"
        
        #Set Default Crawl Account
        $crawlaccount=Get-Account($config.Services.EnterpriseSearch.Account[1])
        $searchApp | Set-SPEnterpriseSearchServiceApplication -DefaultContentAccessAccountName $crawlaccount.Username -DefaultContentAccessAccountPassword $crawlaccount.Password
        
        #Get Search Instance
        $searchInstance = Get-SPEnterpriseSearchServiceInstance $searchServerName
        
        #Get Serach Topology
        $InitialSearchTopology = $searchapp | Get-SPEnterpriseSearchTopology -Active 

        #New Search Topology
        $SearchTopology = $searchapp | New-SPEnterpriseSearchTopology 

        #Create Administration Component and Processing Component
        New-SPEnterpriseSearchAdminComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance
        New-SPEnterpriseSearchAnalyticsProcessingComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance
        New-SPEnterpriseSearchContentProcessingComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance
        New-SPEnterpriseSearchQueryProcessingComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance

        #New Crawl Component
        New-SPEnterpriseSearchCrawlComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance 

        #Index (Query) Component
        New-SPEnterpriseSearchIndexComponent -SearchTopology $SearchTopology -SearchServiceInstance $searchInstance -RootDirectory $IndexLocation 

        #new Search Topology
        $SearchTopology | Set-SPEnterpriseSearchTopology 
	}
	catch
	{	Write-Output $_
	}
}


Trace "Preconfigure Managet Metadata Service" { 
	try
{

      #App Pool     
      $ApplicationPool = Get-SPServiceApplicationPool $config.Services.ManagedMetadata.AppPoolName -ea SilentlyContinue
      if($ApplicationPool -eq $null)
	  { 
            $appoolname=$config.ServiceAppPool.Name
			$appooluser=Get-Account($config.ServiceAppPool.Account)
            $ApplicationPool = New-SPServiceApplicationPool -name $appoolname -account (Get-SPManagedAccount $appooluser.username) 
      }

      #Create a Metadata Service Application
      if((Get-SPServiceApplication |?{$_.TypeName -eq "Managed Metadata Service"})-eq $null)
	  {      
			Write-Host -ForegroundColor Yellow "- Creating Managed Metadata Service:"
            #Get the service instance
            $MetadataServiceInstance = (Get-SPServiceInstance |?{$_.TypeName -eq "Managed Metadata Web Service"})
            if (-not $?) { throw "- Failed to find Metadata service instance" }

             #Start Service instance
            if($MetadataserviceInstance.Status -eq "Disabled")
			{ 
                  Write-Host -ForegroundColor Yellow " - Starting Metadata Service Instance..."
                  $MetadataServiceInstance | Start-SPServiceInstance | Out-Null
                  if (-not $?) { throw "- Failed to start Metadata service instance" }
            } 

            #Wait
			Write-Host -ForegroundColor Yellow " - Waiting for Metadata service to provision" -NoNewline
			While ($MetadataServiceInstance.Status -ne "Online") 
			{
				Write-Host -ForegroundColor Yellow "." -NoNewline
				sleep 1
				$MetadataServiceInstance = (Get-SPServiceInstance |?{$_.TypeName -eq "Managed Metadata Web Service"})
			}
			Write-Host -BackgroundColor Yellow -ForegroundColor Black "Started!"

            #Create Service App
   			Write-Host -ForegroundColor Yellow " - Creating Metadata Service Application..."
            $MetaDataServiceApp  = New-SPMetadataServiceApplication -Name $config.Services.ManagedMetadata.Name -ApplicationPool $ApplicationPool -DatabaseName $config.Services.ManagedMetadata.DBName -HubUri $config.Services.ManagedMetadata.CTHubUrl
            if (-not $?) { throw "- Failed to create Metadata Service Application" }

            #create proxy
			Write-Host -ForegroundColor Yellow " - Creating Metadata Service Application Proxy..."
            $MetaDataServiceAppProxy  = New-SPMetadataServiceApplicationProxy -Name "Metadata Service Application Proxy" -ServiceApplication $MetaDataServiceApp -DefaultProxyGroup
            if (-not $?) { throw "- Failed to create Metadata Service Application Proxy" }
            
			Write-Host -ForegroundColor Yellow "- Done creating Managed Metadata Service."
      }
	  Else {Write-Host "- Managed Metadata Service already exists."}
}

 catch
 {
	Write-Output $_ 
 }
}
#Stop Schritt 3




<?xml version="1.0" encoding="utf-8"?>
<Configurations>
  <Farm ConfigDB="SP_ConfigDB" AdminContentDB="SP_Content_Admin" DatabaseServer="SQLALIAS" Passphrase="assaKdqYrcgOpgBY@6NbmR7cz#20BX">
    <Account Ref="SPFarm" />
    <Email MailServer="SERVER FQDN" FromAddress="sharepoint@domain.ch" Reply="noreply@domain.ch" />
  </Farm>

  <Servers>
    <Server ID="App1" Name="SERVERNAME" />
  </Servers>

  <CentralAdmin Port="7777" AuthProvider="NTLM">
    <Servers>
      <Server Ref="App1" />
    </Servers>
  </CentralAdmin>

  <Accounts>
    <Account ID="SPFarm" Name="domain\sa-spfarm" DisplayName="domain\sa-spfarm" Password="XYZ"></Account>
    <Account ID="SPAppPoolIntranet" Name="domain\sa-spintranet" DisplayName="domain\sa-spintranet" Password="XYZ"></Account>
    <Account ID="SPASServices" Name="domain\sa-spservices" DisplayName="domain\sa-spservices" Password="XYZ"></Account>
    <Account ID="SPASSearchAppPool" Name="domain\sa-spsearch" DisplayName="domain\sa-spsearch" Password="XYZ"></Account>
    <Account ID="SPASSearchAdmin" Name="domain\sa-spsearchadmin" DisplayName="domain\sa-spsearchadmin" Password="XYZ"></Account>
    <Account ID="SPAppPoolMySite" Name="domain\sa-spmysite" DisplayName="domain\sa-spmysite" Password="XYZ"></Account>
  </Accounts>

  <ServiceAppPool Name="SP_ApplicationServices">
    <Account Ref="SPASServices" />
  </ServiceAppPool>

  <Services>
    <BCS Name="Business Data Catalog Service" DBName="SP_AS_BCS" />
    <UsageApplicationService collectioDB="SP_AS_UsageApplication" LogPfad="D:\Microsoft Office Servers\15.0\Logs" />
    <StateService DBName="SP_AS_State" />
    <EnterpriseSearch AppPoolName="SP_AS_Search" DBName="SP_AS_Search">
      <Account Ref="SPASSearchAppPool" />
      <Account Ref="SPASSearchAdmin" />
      <IndexLocation>D:\Microsoft Office Servers\15.0\Data\Office Server\Applications\Index</IndexLocation>
    </EnterpriseSearch>
    <ManagedMetadata Name="Managed Metadata Service" DBName="SP_AS_ManagedMetadata" AppPoolName="SP_ApplicationServices" />
    <UserProfileService Name="User Profile Service" AppPoolName="SP_ApplicationServices">
      <DB>
        <Profile>SP_AS_UPS_Profile</Profile>
        <Sync>SP_AS_UPS_Sync</Sync>
        <Social>SP_AS_UPS_Social</Social>
      </DB>
    </UserProfileService>
  </Services>

  <WebApplications>
	<!-- 1031 Deutsch; 1033 English; 1036 French; 1040 Italian -->
    <WebApplication Name="SP_Intranet" Port="443" WebAppDBName="SP_Content_Intranet" url="https://intranet.domain.ch" SecondaryAdmin="domain\sa-spadmin" RootSiteName="Intranet" WebSitePath="D:\wea\webs\" email="sharepoint@domain.ch" language="1033">
      <Account Ref="SPAppPoolIntranet" />
    </WebApplication>
  </WebApplications>
</Configurations>
#Start Schritt 1
$snapin = Get-PSSnapin Microsoft.SharePoint.Powershell -ErrorVariable err -ErrorAction SilentlyContinue
if($snapin -eq $null){
Add-PSSnapin Microsoft.SharePoint.Powershell 
}


$SP = Get-SPEnterpriseSearchServiceInstance -Identity "vblw2k12spweb1"
$Search = Get-SPEnterpriseSearchServiceInstance -Identity "vblw2k12spapp1"
Start-SPEnterpriseSearchServiceInstance -Identity $SP
Start-SPEnterpriseSearchServiceInstance -Identity $Search
#Stop Schritt 1 und warten bis die SharePoint Such Dienste gestartet sind

#Start Schritt 2 überprüfen, ob alle Such Dienste gestartet sind
Get-SPEnterpriseSearchServiceInstance -Identity $SP
Get-SPEnterpriseSearchServiceInstance -Identity $Search
#Stop Schritt 2

#Start Schritt 3
$ssa = Get-SPEnterpriseSearchServiceApplication
$newTopology = New-SPEnterpriseSearchTopology -SearchApplication $ssa
#Stop Schritt 3

#Start Schritt 4
#Change Topology
New-SPEnterpriseSearchAdminComponent -SearchTopology $newTopology -SearchServiceInstance $Search
New-SPEnterpriseSearchCrawlComponent -SearchTopology $newTopology -SearchServiceInstance $Search
New-SPEnterpriseSearchContentProcessingComponent -SearchTopology $newTopology -SearchServiceInstance $Search
New-SPEnterpriseSearchAnalyticsProcessingComponent -SearchTopology $newTopology -SearchServiceInstance $Search
New-SPEnterpriseSearchQueryProcessingComponent -SearchTopology $newTopology -SearchServiceInstance $SP
New-SPEnterpriseSearchIndexComponent -SearchTopology $newTopology -SearchServiceInstance $SP -IndexPartition 0
#Stop Schritt 4

#Start Schritt 5
Set-SPEnterpriseSearchTopology -Identity $newTopology
#Stop Schritt 5

#OverView
Get-SPEnterpriseSearchTopology -SearchApplication $ssa

#Check if it works
Get-SPEnterpriseSearchStatus -SearchApplication $ssa -Text
#Start Schritt 1
$snapin = Get-PSSnapin Microsoft.SharePoint.Powershell -ErrorVariable err -ErrorAction SilentlyContinue
if($snapin -eq $null){
Add-PSSnapin Microsoft.SharePoint.Powershell 
}

function Write-Info([string]$msg){
    Write-Host "$($global:indent)[$([System.DateTime]::Now)] $msg"
}

function Get-ConfigurationSettings() {
    Write-Info "Loading configuration file."
    [xml]$config = Get-Content ".\Configurations.xml"

    if ($? -eq $false) {
        Write-Info "Cannot load configuration source XML $config."
        return $null
    }
    return $config.Configurations
}

function Trace([string]$desc, $code) {
    trap {
        Write-Error $_.Exception
        if ($_.Exception.InnerException -ne $null) {
            Write-Error "Inner Exception: $($_.Exception.InnerException)"
        }
        break
    }
    $desc = $desc.TrimEnd(".")
    Write-Info "BEGIN: $desc..."
    Set-Indent 1
    &$code
    Set-Indent -1
    Write-Info "END: $desc."
}

function Set-Indent([int]$incrementLevel){
    if ($incrementLevel -eq 0) {$global:indent = ""; return}
    
    if ($incrementLevel -gt 0) {
        for ($i = 0; $i -lt $incrementLevel; $i++) {
            $global:indent = "$($global:indent)`t"
        }
    } else {
        if (($global:indent).Length + $incrementLevel -ge 0) {
            $global:indent = ($global:indent).Remove(($global:indent).Length + $incrementLevel, -$incrementLevel)
        } else {
            $global:indent = ""
        }
    }
}

function Get-Account([System.Xml.XmlElement]$accountNode){
    while (![string]::IsNullOrEmpty($accountNode.Ref)) {
        $accountNode = $accountNode.PSBase.OwnerDocument.SelectSingleNode("//Accounts/Account[@ID='$($accountNode.Ref)']")
    }

    if ($accountNode -eq $null) {
        throw "The account specified cannot be retrieved."
    }
    
    #See if we have the account already as a managed account
    if (([Microsoft.SharePoint.Administration.SPFarm]::Local) -ne $null) {
        [Microsoft.SharePoint.Administration.SPManagedAccount]$account = (Get-SPManagedAccount -Identity $accountNode.Name -ErrorVariable err -ErrorAction SilentlyContinue)
        
        if ([string]::IsNullOrEmpty($err) -eq $true) {
            $accountCred = New-Object System.Management.Automation.PSCredential $account.Username, $account.SecurePassword
            return $accountCred
        }
    }
    if ($accountNode.Password.Length -gt 0) {
        $accountCred = New-Object System.Management.Automation.PSCredential $accountNode.Name, (ConvertTo-SecureString $accountNode.Password -AsPlainText -force)
    } else {
        Write-Info "Please specify the credentials for" $accountNode.Name
        $accountCred = Get-Credential $accountNode.Name
    }
    return $accountCred    
}

function Get-InstallOnCurrentServer([System.Xml.XmlElement]$node){
    if ($node -eq $null -or $node.Server -eq $null) {
        return $false
    }
    $server = $node.Server | where { (Get-ServerName $_).ToLower() -eq $env:ComputerName.ToLower() }
    if ($server -eq $null -or $server.Count -eq 0) {
        return $false
    }
    return $true
}

function Get-ServerName([System.Xml.XmlElement]$node){
    while (![string]::IsNullOrEmpty($node.Ref)) {
        $node = $node.PSBase.OwnerDocument.SelectSingleNode("//Servers/Server[@ID='$($node.Ref)']")
    }
    if ($node -eq $null -or $node.Name -eq $null) { throw "Unable to locate server name!" }
    return $node.Name
}

[System.Xml.XmlElement]$config = Get-ConfigurationSettings

if ($config -eq $null) {
    return $false
}

#Variabeln festlegen
$farmAcct = Get-Account $config.Farm.Account
$configDb = $config.Farm.ConfigDB
$adminContentDb = $config.Farm.adminContentDb
$server = $config.Farm.DatabaseServer
if ($config.Farm.Passphrase.Length -gt 0) {
    $passphrase = (ConvertTo-SecureString $config.Farm.Passphrase -AsPlainText -force)
} else {
    Write-Warning "You didn't enter a farm passphrase, using the Farm Administrator's password instead"
    $passphrase = $farmAcct.Password
}
#Stop Schritt 1

#Start Schritt 2 
Trace "Creating new farm" {
    New-SPConfigurationDatabase -DatabaseName $configDb -DatabaseServer $server -AdministrationContentDatabaseName $adminContentDb -Passphrase $passphrase -FarmCredentials $farmAcct -ErrorVariable err
    if ($err) {
    	throw $err
    }
}
#Stop Schritt 2

#Start Schritt 3
Trace "Verifying farm creation" {
    $farm = Get-SPFarm
    if (!$farm -or $farm.Status -ne "Online") {
        throw "Farm was not created or is not running" 
        exit
    }
}

Trace "Provisioning Central Administration" {
    New-SPCentralAdministration -Port $config.CentralAdmin.Port -WindowsAuthProvider $config.CentralAdmin.AuthProvider -ErrorVariable err
    if ($err) {
        throw $err
    }
}
 
Trace "Install Help Files" {
    Install-SPHelpCollection -All  -ErrorVariable err
    if ($err) {
        throw $err
    }
}
 
Trace "ACLing SharePoint Resources" {
    Initialize-SPResourceSecurity -ErrorVariable err     
    if ($err) {
        throw $err
    }
}

Trace "Installing Services" {
    Install-SPService -ErrorVariable err     
    if ($err) {
        throw $err
    }
}

Trace "Installing Features" {
    Install-SPFeature �AllExistingFeatures -ErrorVariable err 
    if ($err) {
        throw $err
    }
}  

Trace "Installing Application Content" {
    $feature = Install-SPApplicationContent -ErrorVariable err
    if ($err) {
        throw $err
    }
}

Trace "Disable loopback check" {
    New-ItemProperty HKLM:\System\CurrentControlSet\Control\Lsa -Name "DisableLoopbackCheck"  -value "1" -PropertyType dword  -ErrorVariable err
    if ($err) {
        throw $err
    }
}

Trace "Configure Outgoing Email" {
    $email=$config.Farm.Email
    stsadm -o email -outsmtpserver $email.MailServer -fromaddress $email.FromAddress -replytoaddress $email.Reply -codepage 65001
}

Trace "Start Central Administration" {
    $cahost = hostname
    $port=$config.CentralAdmin.Port
    $caurl="http://"+ $cahost + ":" + $port 
    Start-Process "$caurl" -WindowStyle Minimized
}
#Stop Schritt 3