我是PowerShell的新手,我正在尝试编写所有SQL代理作业的脚本。我找到了一段代码,这要归功于SOLID QUALITY MENTORS的ENRIQUE。
我的问题是,如何为每个工作编写一个if存在的脚本? Options.ScriptJobs似乎没有做我认为它应该做的事情?
param([string] $ serverName,[string] $ jobNameFile)
function script-SQLJobs([string] $ server,[string] $ jobNameFile) { [reflection.assembly] :: LoadWithPartialName(“Microsoft.SqlServer.Smo”)| Out-Null
$srv = New-Object Microsoft.SqlServer.Management.Smo.Server("$server")
$db = New-Object Microsoft.SqlServer.Management.Smo.Database
$scrp = New-Object Microsoft.SqlServer.Management.Smo.Scripter($srv)
$scrp.Options.ScriptDrops = $TRUE
$scrp.Options.WithDependencies = $TRUE
$jobNameFile = "C:\SQLJOBS\Jobs.sql"
remove-item $jobNameFile
$jobs = $srv.JobServer.get_Jobs()
$jobs=$jobs | Where-Object {$_.Name -notlike "sys*"}
foreach($job in $jobs)
{
$script=$job.Script()
$script >> $jobNameFile
"GO" >> $jobNameFile
}
}
script-SQLJobs $ serverName $ jobNameFile
非常感谢。
答案 0 :(得分:0)
您可以排除与“drop table”字词不匹配的脚本。例如:
$srv.JobServer.Jobs | Where-Object {$_.Name -notlike "sys*"} | Foreach-Object{
$script = $_.Script()
if($script -notmatch 'DROP TABLE')
{
$script+ "`nGO`n"
}
} | Out-File $jobNameFile
另一个(化妆品)选项是检查所有作业步骤命令:
$srv.JobServer.Jobs | Where-Object {$_.Name -notlike "sys*"} | Foreach-Object{
$cmd = $_.JobSteps | select -expand Command
if($cmd -match 'DROP TABLE')
{
$_.script()+ "`nGO`n"
}
} | Out-File $jobNameFile
答案 1 :(得分:0)
您需要将脚本选项对象提供给脚本方法:
$script=$job.Script($scrp)
答案 2 :(得分:0)
以下是从http://www.johnsansom.com/script-sql-server-agent-jobs-using-powershell/复制的Powershell脚本,该脚本已扩展为您想要的内容。
# Date: 16/02/14
# Author: John Sansom
# Description: PS script to generate all SQL Server Agent jobs on the given instance.
# The script accepts an input file of server names.
# Version: 1.1
#
# Example Execution: .\Create_SQLAgentJobSripts.ps1 .\ServerNameList.txt
param([String]$ServerListPath)
#Load the input file into an Object array
$ServerNameList = get-content -path "Servers.txt"
#$ServerNameList = get-content -path $ServerListPath
#Load the SQL Server SMO Assemly
[System.Reflection.Assembly]::LoadWithPartialName("Microsoft.SqlServer.Smo") | Out-Null
#Create a new SqlConnection object
$objSQLConnection = New-Object System.Data.SqlClient.SqlConnection
#For each server in the array do the following..
foreach($ServerName in $ServerNameList)
{
Try
{
$objSQLConnection.ConnectionString = "Server=$ServerName;Integrated Security=SSPI;"
Write-Host "Trying to connect to SQL Server instance on $ServerName..." -NoNewline
$objSQLConnection.Open() | Out-Null
Write-Host "Success."
$objSQLConnection.Close()
}
Catch
{
Write-Host -BackgroundColor Red -ForegroundColor White "Fail"
$errText = $Error[0].ToString()
if ($errText.Contains("network-related"))
{Write-Host "Connection Error. Check server name, port, firewall."}
Write-Host $errText
continue
}
#IF the output folder does not exist then create it
$OutputFolder = ".\$ServerName"
$DoesFolderExist = Test-Path $OutputFolder
$null = if (!$DoesFolderExist){MKDIR "$OutputFolder"}
#Create a new SMO instance for this $ServerName
$srv = New-Object "Microsoft.SqlServer.Management.Smo.Server" $ServerName
#Script out each SQL Server Agent Job for the server
foreach($job in $srv.JobServer.Jobs)
{
Write-Host $job.Name
$script = ""
$script = $script + "-- Uninstall the job" + "`r`n"
$script = $script + "DECLARE @jobId binary(16)" + "`r`n"
$script = $script + "SELECT @jobId = job_id FROM msdb.dbo.sysjobs WHERE (name = N'$job')" + "`r`n"
$script = $script + "IF (@jobId IS NOT NULL)" + "`r`n"
$script = $script + "BEGIN" + "`r`n"
$script = $script + " EXEC msdb.dbo.sp_delete_job @job_id=@jobId, @delete_unused_schedule=1" + "`r`n"
$script = $script + "END" + "`r`n"
$script = $script + "GO`r`n"
$script = $script + "`r`n"
$script = $script + "-- Install the job" + "`r`n"
$script = $script + $job.Script()
$script = $script + "GO`r`n"
$fileName = $job.Name -replace '\\', ''
$script | out-file ".\$OutputFolder\$fileName.sql"
}
}
注意:您实际上并不想使用SMO创建的DROP命令,因为它取决于作业ID,这使得生成的脚本不可重用。