PowerShell包导入脚本执行时出现#document输出且无报错
问题排查:包导入日志出现异常
#document输出 问题场景
执行PowerShell的ImportPackage函数调用REST接口完成包导入操作,流程显示执行完成且无报错,但日志中出现异常的#document输出,完整执行日志如下:
Package Validation Process Started for - 3. PTW_Dashboards.zip.... Package Validation Process Finished for - 3. PTW_Dashboards.zip Package Import Process Started for - 3. PTW_Dashboards.zip... Reading the Package data... #document Package Import Process Completed for - 3. PTW_Dashboards.zip Logout Process Started... Logout Process completed
对应的ImportPackage函数代码:
function ImportPackage([String] $MeridiumToken, [String] $PackageName, [String] $PkgItems, [String] $DNSURL, [String] $DBConnStr, [String] $DBTableName, [String] $ReleaseID, [String] $pkgID) { try { Write-Host "Package Import Process Started for - $PackageName..." $APIIURL = $DNSURL + '/apm/api/v1/core/metadata/import/selecteditems' # Encode Type $EncodeType = "iso-8859-1" # Dynamic input parameters section $FilePath = "$($env:SYSTEM_DEFAULTWORKINGDIRECTORY)/Subtract-a-thon/Automation/" + $PackageName # Header $IHeaders = @{ 'MeridiumToken' = $MeridiumToken } # Reading Package Write-Host "Reading the Package data..." $FileBinary = [System.IO.File]::ReadAllBytes($FilePath) $Enc = [System.Text.Encoding]::GetEncoding($EncodeType) $FileEnc = $Enc.GetString($FileBinary) $CRLF = "`r`n" $Boundary = [System.Guid]::NewGuid().ToString() # FileName $File_Name = Split-Path $FilePath -leaf # Request Body $IBody = ( "--$Boundary", "Content-Disposition: form-data; name=`"file`"; filename=`"$File_Name`"", "Content-Type: application/octet-stream$CRLF", $FileEnc, $CRLF, "--$Boundary", "Content-Type:application/json", "Content-Disposition: form-data; name=`"items`"$CRLF", $PkgItems, "--$Boundary--" ) -join $CRLF # Request Content Type $IContentType = "multipart/form-data; boundary=`"$boundary`"" # REST Call $ImportLog = Invoke-RestMethod -Uri $APIIURL -Method Post -Headers $IHeaders -ContentType $IContentType -Body $IBody Write-Host $ImportLog Write-Host "Package Import Process Completed for - " $PackageName } catch { Write-Host "An error occurred:" Write-Host $_.ScriptStackTrace throw $_ } }
问题原因
#document输出的直接原因:Invoke-RestMethod调用接口后返回的是XML文档对象([xml]类型),直接使用Write-Host输出该对象时,PowerShell会默认显示其类型标识#document,而非实际的响应内容。潜在的请求构建风险:
手动将二进制文件转成字符串再拼接multipart请求体,可能因编码问题导致文件内容损坏(本次导入成功属于偶然,长期使用可能引发导入失败)。
解决方案
1. 修复#document输出问题
修改Write-Host $ImportLog的代码,将XML对象转为字符串输出:
# 替换原有的Write-Host $ImportLog Write-Host $ImportLog.OuterXml
如果接口可能返回JSON或XML两种格式,可增加类型判断兼容处理:
if ($ImportLog -is [xml]) { Write-Host $ImportLog.OuterXml } else { Write-Host ($ImportLog | ConvertTo-Json -Depth 10) }
2. 优化multipart请求构建(避免编码隐患)
使用PowerShellInvoke-RestMethod原生支持的-Form参数上传文件,无需手动拼接请求体,彻底规避编码问题:
# 删除原手动构建IBody、IContentType的代码,替换为以下内容 $formParams = @{ file = Get-Item -Path $FilePath # 直接传入文件对象 items = $PkgItems # 若PkgItems是JSON字符串,直接传入即可 } # 发起请求 $ImportLog = Invoke-RestMethod -Uri $APIIURL -Method Post -Headers $IHeaders -Form $formParams
内容的提问来源于stack exchange,提问作者Chirantan Mandal
相关产品推荐
相关产品推荐

