在 Octopus 部署中,我在流程中添加了一个步骤,以使用库脚本“SQL - Execute Scripts Ordered step”运行存储过程。
当我提供脚本来执行存储过程时,它会抛出以下异常:
使用“1”个参数调用“ReadAllText”的异常:“指定的路径、文件名或两者都太长。完全限定的文件名必须少于 260 个字符,目录名必须少于 248 个字符。” 关闭连接
我相信这是因为我提供了在“SQL 脚本文件”字段中执行的大型脚本作为文本。 如示例所示,我可以直接运行脚本。所以我提供了存储过程执行脚本,但是在库的 PowerShell scipt -
$content = [IO.File]::ReadAllText($OctopusParameters[‘SqlScriptFile’])
ReadAllText 期望少于 260 个字符。
我能想到的一个解决方案是将执行脚本作为包本身中的文件提供。但这将是最后的手段。
如何直接从进程中的步骤运行存储过程?
显然
[IO.File]::ReadAllText($OctopusParameters[‘SqlScriptFile’])
期望文件路径为 SqlScriptFile。我更新了库的 powershell 脚本以从字段“SQL 脚本文件”中获取完整的 sql 脚本作为参数并将其直接传递给函数。
$content= $OctopusParameters['SqlScriptFile']
Execute-SqlQuery -query $content
下面提供完整的powershell脚本供参考:
$connection = New-Object System.Data.SqlClient.SqlConnection
$connection.ConnectionString = $OctopusParameters['ConnectionString']
Register-ObjectEvent -inputobject $connection -eventname InfoMessage -action {
write-host $event.SourceEventArgs
} | Out-Null
function Execute-SqlQuery($query) {
$queries = [System.Text.RegularExpressions.Regex]::Split($query, "^\s*GO\s*`$", [System.Text.RegularExpressions.RegexOptions]::IgnoreCase -bor [System.Text.RegularExpressions.RegexOptions]::Multiline)
$queries | ForEach-Object {
$q = $_
if ((-not [String]::IsNullOrWhiteSpace($q)) -and ($q.Trim().ToLowerInvariant() -ne "go")) {
$command = $connection.CreateCommand()
$command.CommandText = $q
$command.CommandTimeout = $OctopusParameters['CommandTimeout']
$command.ExecuteNonQuery() | Out-Null
}
}
}
Write-Host "Connecting"
try {
$connection.Open()
Write-Host "Executing script in" $OctopusParameters['SqlScriptFile']
# $content = [IO.File]::ReadAllText($OctopusParameters['SqlScriptFile'])
$content= $OctopusParameters['SqlScriptFile']
Execute-SqlQuery -query $content
}
catch {
if ($OctopusParameters['ContinueOnError']) {
Write-Host $_.Exception.Message
}
else {
throw
}
}
finally {
Write-Host "Closing connection"
$connection.Dispose()
}
SQL - Execute Scripts Ordered 模板 旨在针对 SQL 脚本文件的文件夹运行。
SQL - 执行脚本模板 可能更适合您的场景。